Drupal 8 modules https://publish.mediacurrent.com/ en Design System Integration with PatternKit https://publish.mediacurrent.com/blog/design-system-integration-patternkit <span class="field field--name-title field--type-string field--label-hidden">Design System Integration with PatternKit</span> <div class="clearfix text-formatted field field--name-body field--type-text-with-summary field--label-hidden field__item"><p>The <a href="https://www.drupal.org/project/ui_patterns">UI Patterns</a> module is gaining a lot of traction as an effective way to integrate design patterns and components with Drupal 8, but what if you are still using Drupal 7? The <a href="https://www.drupal.org/project/patternkit">PatternKit</a> module is a viable solution for your site.</p> <p>Traditionally, integrating components from <a href="http://patternlab.io/">Pattern Lab</a> or another design system solution requires a developer to create Drupal templates that map data to components. With PatternKit, the data mapping is handled in the Drupal UI. The user can select the type of component they wish to add to a page and complete the available fields for that element, cutting out the creation and maintenance of an intermediate template file.</p> <p>Besides the fact that these modules are currently available for different versions of Drupal, there is also a difference in the way the UI Patterns and PatternKit modules are integrating design systems. The UI Patterns module turns your design patterns into plugins for your Drupal 8 site, which will create fields even if the component is not used on the site. The PatternKit module is focussed specifically on data mapping in the UI, so that fields and entity types are only created when a component is used. </p> <p>When PatternKit is ported to Drupal 8, the mapping approach might make this module a better choice for enterprise level sites.</p> <p class="text-align-center"> <iframe allow="autoplay; encrypted-media" allowfullscreen="" frameborder="0" height="315" src="https://www.youtube.com/embed/vlVmX7g0ygo" width="560"></iframe></p> <p><strong>Additional Resources</strong><br /> <a href="https://www.mediacurrent.com/blog/inclusive-development-using-style-guides-improve-website-accessibility/">Inclusive Development: Using Style Guides to Improve Website Accessibility</a> | Blog<br /> <a href="https://www.mediacurrent.com/blog/ux-design-evolution-top-uiux-design-trends-2018/">UX Design Evolution: Top UI/UX Design Trends for 2018</a> | Blog</p> </div> <span class="field field--name-uid field--type-entity-reference field--label-hidden"><span lang="" about="/who-we-are/team/april-sides" typeof="schema:Person" property="schema:name" datatype="">April Sides</span></span> <span class="field field--name-created field--type-created field--label-hidden">Mon, 05/21/2018 - 09:33</span> <div class="field field--name-field-tags field--type-entity-reference field--label-above"> <div class="field__label">Tags</div> <div class="field__items"> <div class="field__item"><a href="/tags/ui-patterns" hreflang="en">UI Patterns</a></div> <div class="field__item"><a href="/tags/modules" hreflang="en">Modules</a></div> <div class="field__item"><a href="/tags/pattern-kit" hreflang="en">pattern kit</a></div> <div class="field__item"><a href="/tags/drupal-8-modules" hreflang="en">Drupal 8 modules</a></div> <div class="field__item"><a href="/tags/drupal-8" hreflang="en">Drupal 8</a></div> <div class="field__item"><a href="/tags/drupal-7" hreflang="en">Drupal 7</a></div> </div> </div> <div class="gatsby-iframe-container"><iframe class="gatsby-iframe" src="https://preview-misriptide.gtsb.io/blog/design-system-integration-patternkit"></iframe></div> Mon, 21 May 2018 13:33:47 +0000 April Sides 3257 at https://publish.mediacurrent.com Top Drupal 8 Modules: Drupalcon 2018 Edition https://publish.mediacurrent.com/blog/top-drupal-8-modules-drupalcon-2018-edition <span class="field field--name-title field--type-string field--label-hidden">Top Drupal 8 Modules: Drupalcon 2018 Edition</span> <div class="clearfix text-formatted field field--name-body field--type-text-with-summary field--label-hidden field__item"><p><img alt="Jay Calicott DrupalCon Session" data-entity-type="file" data-entity-uuid="aff55c19-75aa-4cde-9f55-d61413db7f6e" src="/sites/default/files/media/Pic%20JAY.jpg" /></p> <p>Welcome to the latest edition of the top modules for Drupal 8! Below I recap my newest list that I<a href="https://www.youtube.com/watch?v=yrrPN1pfmA4&amp;t=2s"> presented at Drupalcon, Nashville</a> along with updated descriptions. I have also included labels to indicate which modules are best suited for intermediate users versus modules that are universally easy to install and configure.</p> <p>As an added bonus I now have all of these modules and dependencies available through <a href="https://github.com/drupalninja/mc_top_modules">Github</a>/<a href="https://packagist.org/packages/mediacurrent/mc_top_modules">Packagist</a> for easy setup. </p> <p>Just run <em>“composer create-project mediacurrent/mc_top_modules”</em> to get started in minutes, enjoy!</p> <h2>ESSENTIALS LIST</h2> <ol> <li><a href="https://www.drupal.org/project/admin_toolbar">Admin Toolbar</a> (Beginner) - The admin toolbar. It’s a module that you might think would just be in core. We use this on every project because navigating through menus in Drupal is a real pain without rollover menus.</li> <li><a href="https://www.drupal.org/project/components">Component Librarie</a>s (Intermediate) - If you are doing any Twig theming this module is going to help you with your Twig file includes.</li> <li><a href="https://www.drupal.org/project/devel">Devel </a>(Intermediate) - Devel can help you debug problems in Twig templates. Another feature that is handy is the ability to generate dummy content.</li> <li><a href="https://www.drupal.org/project/entity_browser">Entity Browser</a> / <a href="https://www.drupal.org/project/media_entity_browser">Media Entity Browser </a>(Beginner) - The Media Entity Browser module gives you the ability to use a nice little library pop-up to upload, browse and search for different types of media.</li> <li><a href="https://www.drupal.org/project/field_group">Field Group</a> (Beginner) - This is a helpful module for cleaning up your content types. You can organize fields into tabs, accordions, etc. to give your content editors a better experience.</li> <li><a href="https://www.drupal.org/project/google_analytics">Google Analytics</a> (Beginner) - Google Analytics is a simple module that allows site admins the ability to easily add basic tracking.</li> <li><a href="https://www.drupal.org/project/linkit">Linkit</a> (Beginner) - This module gives you an autocomplete popup inside of Wysiwyg for adding links.</li> <li><a href="https://www.drupal.org/project/metatag">Metatag</a> (Beginner) - Maintained by Mediacurrent’s very own Damien McKenna, this module lets you configure all of your meta tags for SEO purpose.</li> <li><a href="https://www.drupal.org/project/panels">Panels</a> / <a href="https://www.drupal.org/project/ctools">CTools</a> / <a href="https://www.drupal.org/project/page_manager">Page Manager </a>(Intermediate) - Panels is a great site building tool for creating custom layouts with a drag and drop interface.</li> <li><a href="https://www.drupal.org/project/paragraphs">Paragraphs</a> / <a href="https://www.drupal.org/project/entity_reference_revisions">Entity Reference Revisions</a> (Intermediate) - The paragraphs module is a Mediacurrent favorite for a couple of reasons. Paragraphs are like mini-content types that can handle a variety of use cases.</li> <li><a href="https://www.drupal.org/project/pathauto">Pathauto</a> / <a href="https://www.drupal.org/project/token">Token</a> (Beginner) - The pathauto module lets you set up clean alias patterns for all of your content. If you want all of your blogs to have the path /blog/[title of the blog with hyphens instead of spaces] - this will be the module that you use.</li> <li><a href="https://www.drupal.org/project/redirect">Redirect</a> (Beginner) - Almost every new site needs to incorporate 301 redirects for old page URLs. The redirect module gives site admins an easy interface for creating those redirects in Drupal.</li> <li><a href="https://www.drupal.org/project/search_api">Search API</a> (Intermediate) - The Search API suite of modules is a fantastic way to configure your site searches. By default this Search API DB is enabled but you can easily swap out for Apache Solr. The Search API Pages module is also handy for getting a site search up and running quickly.</li> <li><a href="https://www.drupal.org/project/simple_sitemap">Simple Sitemap</a> (Intermediate) - A pretty easy to configure module for creating XML sitemaps for search engines.</li> <li><a href="https://www.drupal.org/project/stage_file_proxy">Stage file proxy </a>(Beginner) - A great module for downloading images to your local environment auto-magically rather than having to continually migrate those images manually.</li> <li><a href="https://www.drupal.org/project/webform">Webform</a> (Beginner) - This module is awesome because it makes it easy to make any and all kinds of forms on your site. This is a must-have module if you plan on managing forms within Drupal.</li> </ol> <h2>NOTABLE MENTIONS</h2> <p>Below are a list of notable mentions that didn’t make the essentials list but are still worth checking out.</p> <ol> <li><a href="https://www.drupal.org/project/ckeditor_media_embed">CKEditor Media Embed</a> (Beginner) - A lot of content out there on the web includes social media callouts. This module makes it a lot to easier to include that content inside of your Wysiwyg.</li> <li><a href="https://www.drupal.org/project/colorbox">Colorbox</a> (Beginner) - The Colorbox module integrates is a popular lightbox library of the same name with Drupal Views and fields. You will need to download the Colorbox library to your libraries folder, otherwise this module is very easy to set up.</li> <li><a href="https://www.drupal.org/project/commerce">Commerce</a> (Intermediate) - If you have done any e-Commerce you have probably heard about the <em>Commerce</em> suite of modules for Drupal. This allows you to add products to your site and checkouts, payment options and more.</li> <li><a href="https://www.drupal.org/project/dropzonejs">DropzoneJS</a> (Intermediate) - Pretty much everywhere you go on the web you see a drag and drop upload option. So why not have that in your Drupal project? This module makes it relatively easy to do so but there is some configuration required along with the need to download the DropzoneJS library.</li> <li><a href="https://www.drupal.org/project/entity_embed">Entity embed</a> / <a href="https://www.drupal.org/project/embed">Embed</a> (Intermediate) - This module lets you embed any Drupal entity anywhere. The most common use case for this is embedding media within Wysiwyg. When paired with the Media Entity Browser, for example this gives editors a powerful tool for embedding media from a library. Both the Lightning &amp; Thunder distributions have good examples of this implementation.</li> <li><a href="https://www.drupal.org/project/extlink">External Links</a> (Beginner) - Over the years we have seen that most clients want the option to force external links to open up in a new window or tab. This module makes that feature request very easy. All you do is check one checkbox and essentially you are done.</li> <li><a href="https://www.drupal.org/project/focal_point">Focal point </a>/ <a href="https://www.drupal.org/project/crop">Crop</a> (Intermediate) - The problem we are trying to solve with these modules is supporting different kinds of crops from the same source image. This solution is probably the easiest I’ve found both on the developer and the content editor. This module tries to crop around the focus of the image rather than just arbitrarily cropping from the center.</li> <li><a href="https://www.drupal.org/project/geolocation">Geolocation</a> (Beginner) - I like that the Geolocation module makes it simple to add a point on a map and have that map render in a field. Easy to input and easy to format, with plenty of options for configuration.</li> <li><a href="https://www.drupal.org/project/honeypot">Honeypot</a> (Beginner) - Do you ever get spam? While there are a lot of options for anti-spam measures (including captches) this solution has an algorithm that does not burden the end user and is pretty effective.</li> <li><a href="https://www.drupal.org/project/lightning">Lightning Install Profile </a>(Beginner) - Lightning is a general purpose Drupal distribution that focuses on the media and editorial enhancements. Not only is it a good started distribution for Drupal development, it is also a good learning tool. It often is easier to learn how to configure and use a module by examining how it’s implemented on a pre-configured distribution like Lightning.</li> <li><a href="https://www.drupal.org/project/scheduler">Scheduler</a> (Beginner) - The scheduler module lets you schedule the publishing and unpublishing of your content. Note that it is going to use cron to make this happen so you need to verify that your cron is configured correctly.</li> <li><a href="https://www.drupal.org/project/slick">Slick</a> / <a href="https://www.drupal.org/project/slick_views">Slick views</a> / <a href="https://www.drupal.org/project/slick_media">Slick media</a> (Intermediate) - The Slick suite of modules adds functionality to allow site builders to create slideshows and carousels. There are several related modules that integrate with every aspect of Drupal. The hardest part is the initial setup of library dependencies. Once that is done these modules are very easy to configure within the Drupal admin.</li> <li><a href="https://www.drupal.org/project/taxonomy_access_fix">Taxonomy Access Fix </a>(Beginner) - This project addresses the fact that core doesn’t have granular enough permissions. The Taxonomy Access Fix module therefore adds in additional permissions to fill in the gaps.</li> <li><a href="https://www.drupal.org/project/viewsreference">Viewsreference</a> (Beginner) - Last but not least the Viewsreference module gives editors the ability to select a View from a field. At Mediacurrent we combine this field with a Paragraph type to give editors an easy, flexible interface for embedding Views onto a page.</li> </ol> <p>Did I miss any modules you think should have made this list? Let me know on Twitter at <a href="https://twitter.com/drupalninja">@drupalninja</a>!</p> <p><strong>Additional Resources</strong><br /> <a href="https://www.mediacurrent.com/blog/top-drupal-7-modules-final-edition/">Top Drupal 7 Modules: Final Edition</a> | Blog<br /> <a href="https://www.mediacurrent.com/blog/top-drupal-marketing-automation-modules/">Top Drupal Marketing Automation Modules</a> | Blog<br /> <a href="https://www.mediacurrent.com/blog/top-reasons-choose-drupal/">Top Reasons to Choose Drupal </a>| Blog</p> </div> <span class="field field--name-uid field--type-entity-reference field--label-hidden"><a title="View user profile." href="/who-we-are/team/jay-callicott" lang="" about="/who-we-are/team/jay-callicott" typeof="schema:Person" property="schema:name" datatype="" class="username">Jay Callicott</a></span> <span class="field field--name-created field--type-created field--label-hidden">Tue, 05/08/2018 - 08:18</span> <div class="field field--name-field-services field--type-entity-reference field--label-above"> <div class="field__label">Services</div> <div class="field__item"><a href="/service/development" hreflang="en">Development</a></div> </div> <div class="field field--name-field-tags field--type-entity-reference field--label-above"> <div class="field__label">Tags</div> <div class="field__items"> <div class="field__item"><a href="/tags/drupal-8-modules" hreflang="en">Drupal 8 modules</a></div> <div class="field__item"><a href="/tags/module" hreflang="en">Module</a></div> <div class="field__item"><a href="/tags/drupal" hreflang="en">Drupal</a></div> <div class="field__item"><a href="/tags/drupalcon-nashville" hreflang="en">DrupalCon Nashville</a></div> </div> </div> <div class="field field--name-field-redirects field--type-string-long field--label-above"> <div class="field__label">Redirects</div> <div class="field__item">/blog/mediacurrent-top-drupal-8-modules-drupalcon-2018-edition/</div> </div> <div class="field field--name-field-related-content field--type-entity-reference field--label-above"> <div class="field__label">Related Content</div> <div class="field__items"> <div class="field__item"><a href="/blog/state-drupal-2019" hreflang="en">The State of Drupal in 2019</a></div> </div> </div> <div class="gatsby-iframe-container"><iframe class="gatsby-iframe" src="https://preview-misriptide.gtsb.io/blog/top-drupal-8-modules-drupalcon-2018-edition"></iframe></div> Tue, 08 May 2018 12:18:51 +0000 Jay Callicott 3253 at https://publish.mediacurrent.com Autocomplete Deluxe Released for D8 https://publish.mediacurrent.com/blog/autocomplete-deluxe-released-d8 <span class="field field--name-title field--type-string field--label-hidden">Autocomplete Deluxe Released for D8</span> <div class="clearfix text-formatted field field--name-body field--type-text-with-summary field--label-hidden field__item"><p>I am excited to announce that the D8 port of the <a href="https://www.drupal.org/project/autocomplete_deluxe">Autocomplete Deluxe</a> module has been released in “beta”!</p> <h2>What does it do?</h2> <p>The Autocomplete Deluxe module provides a widget that enhances the default autocomplete field in Drupal. It uses jQuery UI autocomplete and provides a slick visual element for content editors to reference terms - displaying them inline, drag-n-drop reordering, and creation of new terms from the field itself. It works out-of-the-box and no 3rd party libraries are needed.</p> <h2>Installation and setup</h2> <p>Installing this module is straightforward - especially for Drupal 8. Simply run:</p> <pre> <code class="language-bash">composer require drupal/autocomplete_deluxe;</code></pre><p>To set up a field called “Tags" to use the Autocomplete Deluxe widget to set<br /> values from the “Tags” taxonomy:</p> <ul> <li>Navigate to “Administration” &gt; “Modules” and enable the “Autocomplete Deluxe” module.</li> <li>Navigate to “Administration”  &gt; “Structure” &gt; “Content types” and select “Manage fields” of the content type you wish to edit.</li> <li>Add a new field of "Term reference" named "Tags".</li> <li>Select the “Tags” vocabulary and save field settings.</li> <li>Under the “Manage form display” tab, select the "Autocomplete Deluxe" widget type in the dropdown menu for your field and save.</li> <li>Customize or keep the default Autocomplete Deluxe widget field settings.</li> </ul> <p>And that’s pretty much it!</p> <p>When you visit your node’s add or edit page, you will see the terms referenced displayed in the Autocomplete Deluxe widget:</p> <p><img alt="Autocomplete Deluxe Released for D8" class="media-element file-default media-wysiwyg-align-center" data-delta="1" data-entity-type="" data-entity-uuid="" src="https://publish.mediacurrent.com/sites/default/files/va-bef450mjlixy4zvlarger1w21kykgk2hdujkklonnulpmkx9qh1iqoyk9jk5gkzvqu8sf6t2gtzkk4a3gogietc0x857cb4jpqk798he_lr_yaboacb_jbbn8s7omhzwgjtju.png" title="Autocomplete Deluxe Released for D8" typeof="foaf:Image" /></p> <p>Additional information can be found in the <a href="http://cgit.drupalcode.org/autocomplete_deluxe/tree/README.txt?h=8.x-1.x">README</a>.</p> <h2>Contributions and attributions</h2> <p>As of this blog post, there are <a href="https://www.drupal.org/project/usage/autocomplete_deluxe">14,374 sites using the module</a> (with 159,221 downloads) on D7 and I anticipate that number will continue to ascend as more D8 sites use it.</p> <p>The D8 port of the module started with an <a href="https://www.drupal.org/node/2754715">issue</a> created in June 2016 and has been made possible through contributions from several members of the community - notably <a href="https://www.drupal.org/u/idtarzanych">@idtarzanych</a>, Mediacurrent’s own <a href="https://www.drupal.org/u/LNakamura">@LNakamura</a>, and myself. Working from the initial patch provided by @idtarzanych, we were able to make some minor updates to ensure D8 standards were followed and was rid of PHPCS errors.</p> <p>Mediacurrent acquired maintainership status of the Autocomplete Deluxe module from the module creator, <a href="http://epiqo.com/">Epiqo</a>, in July 2017 - and we’ve been committing to the effort of assuring the issue queue is groomed, up-to-date, and responding to issues in a timely manner. <a href="https://www.mediacurrent.com/about/our-team/lee-nakamura">Lee Nakamura</a> and I are excited to continue to keep this module up to its full potential.</p> <p>We hope that you will be able to make use of this wonderful module on your D8 sites and look forward to working on making it better through community contributions and feedback.</p> </div> <span class="field field--name-uid field--type-entity-reference field--label-hidden"><span lang="" about="/who-we-are/team/edward-chan" typeof="schema:Person" property="schema:name" datatype="">Edward Chan</span></span> <span class="field field--name-created field--type-created field--label-hidden">Thu, 09/07/2017 - 11:11</span> <div class="field field--name-field-tags field--type-entity-reference field--label-above"> <div class="field__label">Tags</div> <div class="field__items"> <div class="field__item"><a href="/tags/drupal" hreflang="en">Drupal</a></div> <div class="field__item"><a href="/tags/autocomplete" hreflang="en">Autocomplete</a></div> <div class="field__item"><a href="/tags/drupal-8-modules" hreflang="en">Drupal 8 modules</a></div> <div class="field__item"><a href="/tags/how" hreflang="en">how to</a></div> </div> </div> <div class="field field--name-field-related-content field--type-entity-reference field--label-above"> <div class="field__label">Related Content</div> <div class="field__items"> <div class="field__item"><a href="/blog/typescript-and-drupalbehaviors" hreflang="en">TypeScript and Drupal.behaviors</a></div> <div class="field__item"><a href="/blog/building-rest-endpoints-drupal-8" hreflang="en">Building REST Endpoints with Drupal 8 </a></div> <div class="field__item"><a href="/blog/creating-content-yaml-content-module" hreflang="en">Creating Content with YAML Content Module</a></div> </div> </div> <div class="gatsby-iframe-container"><iframe class="gatsby-iframe" src="https://preview-misriptide.gtsb.io/blog/autocomplete-deluxe-released-d8"></iframe></div> Thu, 07 Sep 2017 15:11:07 +0000 Edward Chan 3071 at https://publish.mediacurrent.com Integrating Amazon Alexa With a Drupal 8 Site https://publish.mediacurrent.com/blog/integrating-amazon-alexa-drupal-8-site <span class="field field--name-title field--type-string field--label-hidden">Integrating Amazon Alexa With a Drupal 8 Site</span> <div class="clearfix text-formatted field field--name-body field--type-text-with-summary field--label-hidden field__item"><p>If you’ve ever used Alexa, it may seem like it must be extremely complicated to get her to respond like she does. However, if you have your content inside Drupal, it’s not terribly difficult to get her to utilize that data for your own custom Alexa skill. Let’s take a look at how to accomplish that.</p> <h2>Add the Alexa module to your website </h2> <p>To have your website talk to Amazon, it has to be seen by Amazon’s servers. With that said, your site will have to be outward facing with an https domain. This isn’t an endorsement for them but for this example, we’ll be using a Pantheon hosted site, which allows for free Drupal dev sites to be quickly spun up. To implement this, the first thing we will need to do is add the <a href="https://www.drupal.org/project/alexa">Alexa module </a>to our Drupal 8 site.</p> <h2>Set up an Alexa Skill on the Amazon Developer site </h2> <p>After your site is up and you have the module installed, it’s time to start setting up the Amazon side of things. You’ll first need to create a developer account at <a href="https://developer.amazon.com/">https://developer.amazon.com</a>. Next, you’ll need to set up a new Alexa Skill.</p> <p><img alt="Amazon Alexa Skills Kit" class="media-element file-default media-wysiwyg-align-center" data-delta="2" data-entity-type="" data-entity-uuid="" src="https://publish.mediacurrent.com/sites/default/files/umryu7w4hyexvlwow5tksabjqszxjo8asim-1agp-szkyuyiapnaujjxhyobfjwespfaxdydfgzyrm_dovq4wc-xcnp3zfbmst0_c17hv1buxy8quznswx1ozduzwsgg4gsixdef_0.png" title="Amazon Alexa Skills Kit" typeof="foaf:Image" /></p> <p>Once you’ve created a new Alexa skill, it’s time to start configuring it to be able to reach our site. The first thing to note is the Application ID that Amazon provides to you. That will need to be copied into the Alexa modules config located on your site at /admin/config/services/alexa</p> <p><img alt="Alexa Configuration" class="media-element file-default media-wysiwyg-align-center" data-delta="12" data-entity-type="" data-entity-uuid="" src="https://publish.mediacurrent.com/sites/default/files/amazon2.png" title="Alexa Configuration" typeof="foaf:Image" /></p> <p>Next, back on the Amazon Development site, give your app a Name and an Invocation Name. The Invocation Name is what the end user will have to utter in order to activate the skill. For our example, we’ll be using the Invocation Name of ‘world publish’.</p> <p><img alt="Amazon Alexa Configuration" class="media-element file-default media-wysiwyg-align-center" data-delta="13" data-entity-type="" data-entity-uuid="" src="https://publish.mediacurrent.com/sites/default/files/amazon1.png" title="Amazon Alexa Configuration" typeof="foaf:Image" /></p> <p>Next, click on Interaction Model. This is where we will begin to setup our custom commands that Alexa can respond to. These commands are called intents. Here we have setup 2 custom intents, readArticle and WorldPublish.</p> <p><img alt="Amazon Interaction Model" class="media-element file-default media-wysiwyg-align-center" data-delta="5" data-entity-type="" data-entity-uuid="" src="https://publish.mediacurrent.com/sites/default/files/mkk1zomyagcxqnih0zxzxem-yrmecrsotqg44b_og_01onn65l6eviz7hsrtsv67hrbgecclnoq6oga6mu8bpwz51trdxyjienyioorhclc6d967xgvdggojm_xkiq9ubcf9qde.png" title="Amazon Interaction Model" typeof="foaf:Image" /></p> <p>The other four listed are the default intents that Amazon provides to all Alexa apps and won’t require any setup on this side from us (though we will set a custom value for the AMAZON.HelpIntent when we are writing our custom module).</p> <p>Our WorldPublish intent here will be used to ask Alexa what the five latest articles are on our site.</p> <p><img alt="Alexa WordPublish" class="media-element file-default media-wysiwyg-align-center" data-delta="6" data-entity-type="" data-entity-uuid="" src="https://publish.mediacurrent.com/sites/default/files/9t9ahko7bpdwyjzl-i6935tjj9ev7ddd61o1sw2a6hsojyaybzypbw9itilx8zzdpbdozr7kww-rkakbxjlcrumdswbok-wqomtf0muoe3ft2jeaidadgg2tuh5sur2zarig1szm.png" title="Alexa WordPublish" typeof="foaf:Image" /></p> <p>To have a better chance the user utters the right intent,  you can add more phrasings of this same question to make sure Alexa still will respond appropriately. In our custom module, we will set up the actions required for Alexa to respond back to this question by reading out the titles of the latest articles by date.</p> <p>Once Alexa has given the user the names of the newest articles, the user may want one of those articles read to them. In our readArticle intent, we create two ways for the user to get an article read back to them. This intent also shows how we can use variables in our command. This variable will be sent to our custom module where we can use that to pull in the name of the article we want Alexa to read back to us.<br />  </p> <h2>Create custom module for your responses </h2> <p>Now that we have some intents for Alexa to use, it’s time to start writing some code for what happens when a command is sent to your website. We’ll be naming the module demo_alexa.</p> <p>In the demo_alexa.info.yml file put in the following:</p> <pre> <code class="language-yaml">name: Alexa Latest Articles Demo type: module description: Demonstrates an integration to Amazon Echo. core: 8.x package: Alexa dependencies: - alexa</code></pre><!-- HTML generated using hilite.me --><p>Be sure to add the Alexa module as a dependency. Next, we need to create the file that will do all the heavy lifting in our custom module. Create a file inside src/EventSubscriber/ and call it RequestSubscriber.php</p> <p><img alt="Request Subscriber PHP" class="media-element file-default media-wysiwyg-align-center" data-delta="8" data-entity-type="" data-entity-uuid="" src="https://publish.mediacurrent.com/sites/default/files/v1m4hsny7xxyz2wgdnjoc-u8nuhpvcs0dgeepzrlunxba3tmkpc4_xobhhd4wsplxwmbh2jqtlr1by_6klyqc-lx6btlfwhk_b0j-u2tohvygshkbl0gxug8-svltq1dz57dr9zm.png" title="Request Subscriber PHP" typeof="foaf:Image" /></p> <p>Let’s break down what code goes into this file. First, we need to create a namespace and our use statements.</p> <pre> <code class="language-php">namespace Drupal\demo_alexa\EventSubscriber; use Drupal\alexa\AlexaEvent; use Symfony\Component\EventDispatcher\EventSubscriberInterface; use Drupal\paragraphs\Entity\Paragraph;</code></pre><!-- HTML generated using hilite.me --><p>Next, we need to make our main class and a function that gets the event.</p> <pre> <code class="language-php">/**  * An event subscriber for Alexa request events.  */ class RequestSubscriber implements EventSubscriberInterface {   /**   * Gets the event.   */   public static function getSubscribedEvents() {   $events['alexaevent.request'][] = ['onRequest', 0];   return $events;   }</code></pre><!-- HTML generated using hilite.me --><p>Now we can make the function that gives responses for each of our intents. Here’s the code for that:</p> <pre> <code class="language-php">/**  * Called upon a request event.  *  * @param \Drupal\alexa\AlexaEvent $event  * The event object.  */ public function onRequest(AlexaEvent $event) { $request = $event-&gt;getRequest();   $response = $event-&gt;getResponse();   switch ($request-&gt;intentName) {   case 'AMAZON.HelpIntent':   $response-&gt;respond('You can ask "what are the latest articles" and I will read the titles to you');   break;   case 'WorldPublish':   $latestArticles = current_posts_contents();   $response-&gt;respond($latestArticles);   break;   case 'readArticle':   $article = $request-&gt;getSlot('Article');   $articleResponse = current_post_body($article);   $response-&gt;respond($articleResponse);   break;   default:   $response-&gt;respond('Hello World Publish User. I can tell you the latest articles.');   break;   } }</code></pre><!-- HTML generated using hilite.me --><p>Here you can see the name of our two custom intents that we created earlier, WorldPublish and readArticle. You can also see how this can be used to set values for the default intents such as AMAZON.HelpIntent where when the user asks Alexa for help, we now have a custom response that Alexa will respond back to the user with. This function also gives us the ability to set a default response for if Alexa doesn’t understand what the question was. This is a good place to give the user the phrasing needed to get the proper response from Alexa.</p> <p>Let’s take a look in more detail at the two custom intents we have in the code above. First off we have the WorldPublish intent.</p> <pre> <code class="language-php"> case 'WorldPublish': $latestArticles = current_posts_contents(); $response-&gt;respond($latestArticles); break;</code></pre><!-- HTML generated using hilite.me --><p>If the WorldPublish intent is the one the user uttered, then we’ll run a custom function named current_posts_contents and then Alexa will respond back with the response from that function. Here is what that custom current_posts_contents function is doing:</p> <pre> <code class="language-php">/**  * Get latest articles function.  *  * Set beginning and end dates, retrieve posts from database  * saved in that time period.  *  * @return array  * A result set of the targeted posts.  */ function current_posts_contents() {   $query = \Drupal::entityQuery('node');   // Return the newest 5 articles.   $newest_articles = $query-&gt;condition('type', 'article')   -&gt;condition('status', 1)   -&gt;sort('created', 'DESC')   -&gt;pager(5);   $nids = $query-&gt;execute();   $fullstring = 'Here are the five latest articles from WorldPublish, ';   foreach ($nids as $nid) {   $node = \Drupal::entityTypeManager()-&gt;getStorage('node')-&gt;load($nid);   $name = $node-&gt;getTitle();   $fullstring = $fullstring . ' ' . $name . ',';   }   $fullstring = $fullstring . '. You can have me &lt;phoneme alphabet="ipa" ph="ɹˈiːd"&gt;read&lt;/phoneme&gt; you one of the articles by saying, Alexa read, and then the title of the article.';     return($fullstring); }</code></pre><!-- HTML generated using hilite.me --><p>This function does a query of the content type named ‘article’, with the condition that the status is set to publish, ordered by when the article was created and set to return the first five results. This query will give us an array of nid’s that we can use in a foreach loop . We then load the title of the nid and append that title to a string that will be Alexa’s response.</p> <p>Another thing to note in this code is that sometimes, Alexa won’t get the phonetic pronunciation of words correct. In the statement “You can have me read you one of the articles”, Alexa was saying “red” instead of “reed” when pronouncing “read”. To correct that we can use the Speech Synthesis Markup Language to directly tell Alexa how to pronounce a specific word. To get the correct sounds, you can use the <a href="https://developer.amazon.com/public/solutions/alexa/alexa-skills-kit/docs/speech-synthesis-markup-language-ssml-reference#supported-symbols">phoneme alphabet</a> that is provided on Amazon’s help site.</p> <pre> <code class="language-twig">&lt;phoneme alphabet="ipa" ph="ɹˈiːd"&gt;read&lt;/phoneme&gt;</code></pre><!-- HTML generated using hilite.me --><p>By using the phoneme alphabet in this code, Alexa will change her pronunciation to the correct way to say the word “read” in this sentence.</p> <p>Now that we have had Alexa read us a list of the five latest articles, let’s take a look at the readArticle case:</p> <pre> <code class="language-php"> case 'readArticle': $article = $request-&gt;getSlot('Article'); $articleResponse = current_post_body($article); $response-&gt;respond($articleResponse); break;</code></pre><!-- HTML generated using hilite.me --><p>So here we can see where our ‘Article’ variable we set in our intent on the Amazon Developer site comes into play. We’re first grabbing that value from what the user tells Alexa and storing it inside of $article. Then we’re sending that value to a custom function called current_post_body to get our article for Alexa to read. Here’s what’s inside that function:</p> <pre> <code class="language-php">/**  * Get body of an article.  *  * Get body of article based on title.  *  * @return array  * A result set of the targeted posts.  */ function current_post_body(&amp;$article) {   $query = \Drupal::entityQuery('node');   // Return the newest 5 articles.   $article_query = $query-&gt;condition('type', 'article')   -&gt;condition('status', 1)   -&gt;condition('title', $article, 'CONTAINS')   -&gt;sort('created', 'DESC')   -&gt;pager(1);   $nids = $query-&gt;execute();   if ($nids) {   foreach ($nids as $nid) {   $node = \Drupal::entityTypeManager()-&gt;getStorage('node')-&gt;load($nid);   $name = $node-&gt;getTitle();   $foo = '';   foreach ($node-&gt;field_paragraph as $item) {   $target_id = $item-&gt;target_id;   $paragraph_node = Paragraph::load($target_id);   $addition = $paragraph_node-&gt;field_wysiwyg-&gt;value;   // Remove html tags from value.   $addition = strip_tags($addition);   $foo = $foo . $addition;   }   }   $response = $response . 'Here is the article, ' . $name . '. ' . $foo;   }   else {   $response = 'I do not see an article by that name. To have me list the latest 5 articles, say, alexa what are the latest articles.';   }   return($response); }</code></pre><!-- HTML generated using hilite.me --><p>First thing this code does is it runs a query looking through the published article nodes looking for a title that contains the string that the user input. It will then return the latest article it can find that contains that string. From there if we found a piece of content that matches up, we then grab all the values from the paragraph fields inside our article. Just a note that if you aren’t using <a href="https://www.drupal.org/project/paragraphs">paragraph fields</a> for your content then this is where you could return whichever fields you wanted Alexa to read back. Lastly, our code then strips out any html tags from the created string so all that is left is the text of the article. This string is now ready to be given back to Alexa for her response.</p> <p>Now that we have our code for our responses back to Alexa, the last file we’ll need is demo_alexa.services.yml</p> <pre> <code class="language-yaml">services: alexa_demo.request_subscriber: class: Drupal\demo_alexa\EventSubscriber\RequestSubscriber   tags:   - { name: event_subscriber }</code></pre><!-- HTML generated using hilite.me --><p> </p> <p>This should be all the code you’ll need to now test out your Alexa skill. Be sure to enable your demo Alexa module and then head back over to the Amazon Developer site.</p> <h2>Test the responses from the Amazon Developer Site </h2> <p>Back at developer.amazon.com click on the Test tab and make sure your skill is enabled for testing on your account.</p> <p><img alt="Amazon Developer Site" class="media-element file-default media-wysiwyg-align-center" data-delta="9" data-entity-type="" data-entity-uuid="" src="https://publish.mediacurrent.com/sites/default/files/ewaso1gltjj5n32pmk8aepot6q6palscgdrd2onuomvaf2ecgscilg_bt3p4yjixpid_mmaukkvtaddrjyuzigv9li2dgpjcjlghentctmwb-zw6instqbavhh3cwgbt5oje6tyg.png" title="Amazon Developer Site" typeof="foaf:Image" /></p> <p>As of the time of this blog posting, there’s currently an issue with the test text simulator not working correctly but there’s an easy workaround for that. Be sure on “Use Service Simulator to test your HTTPS endpoint” that your web domain is listed in the box. Then you should be ready to enter in an Utterance into the text box. Type “help” into the box and this will send that to our code we just wrote. When you click the submit button it should send the AMAZON.HelpIntent request to our code and our code will respond back with the custom response we gave.</p> <p><img alt="Amazon Test Text Simulator" class="media-element file-default media-wysiwyg-align-center" data-delta="10" data-entity-type="" data-entity-uuid="" src="https://publish.mediacurrent.com/sites/default/files/mjjauez7jtpvtqfuboldvpry4kflk7s9ye7h8oiuwhrtm4gpoymopcjivoiopqdb2yljyz-wmx6dsgfj4vllpas_p42bkvq0jiu284-sfu1vf2yvv5fees-okdbqjp7wziy05oyz.png" title="Amazon Test Text Simulator" typeof="foaf:Image" /></p> <p>As you can see though, it looks like it didn’t work. This is the issue that Amazon is aware of and is currently fixing. We can get by this though by copying everything inside the Service Request box and then pasting it into the Json Request box in the JSON tab.</p> <p>You can then click on ‘Listen’ and you’ll hear Alexa repeat back what the website sent as the response! You can try it again by asking Alexa ‘What are the latest articles’ and if you have articles on your site it should list out the articles for you.</p> <p>Here’s a quick video showing this custom module working using an Amazon Echo Dot. This shows off how to activate the demo on the Echo, the commands for listing the articles, reading the article specified and also one of the built in default commands to stop Alexa talking. Be warned that if you have an Echo in your room with you, it will also try to respond to the commands said in this video as well!</p> <p><iframe frameborder="0" height="315" src="https://www.youtube.com/embed/Y82eLac2y3Q" width="560"></iframe></p> <p>So that’s it! With this code, you have a good example of how easy it can be to get Alexa to talk to your website. This could easily be used to create lots of different, fun interactive ways for your users to access all of the various content on your Drupal website.</p> <p><strong>Additional Resources</strong><br /> <a href="https://www.mediacurrent.com/blog/building-rest-endpoints-drupal-8">Building Rest Endpoints with Drupal 8</a> | Blog<br /> <a href="https://www.mediacurrent.com/blog/creating-content-yaml-content-module">Creating Content with YAML Content Module </a>| Blog<br /> <a href="https://www.mediacurrent.com/blog/mediacurrents-drupal-theme-generator">Mediacurrent's Drupal Theme Generator</a> | Blog</p> </div> <span class="field field--name-uid field--type-entity-reference field--label-hidden"><span lang="" about="/who-we-are/team/sam-seide" typeof="schema:Person" property="schema:name" datatype="">Sam Seide</span></span> <span class="field field--name-created field--type-created field--label-hidden">Wed, 08/16/2017 - 08:31</span> <div class="field field--name-field-tags field--type-entity-reference field--label-above"> <div class="field__label">Tags</div> <div class="field__items"> <div class="field__item"><a href="/tags/amazon-alexa" hreflang="en">Amazon Alexa</a></div> <div class="field__item"><a href="/tags/drupal" hreflang="en">Drupal</a></div> <div class="field__item"><a href="/tags/web-design" hreflang="en">web design</a></div> <div class="field__item"><a href="/tags/drupal-8-modules" hreflang="en">Drupal 8 modules</a></div> </div> </div> <div class="field field--name-field-related-content field--type-entity-reference field--label-above"> <div class="field__label">Related Content</div> <div class="field__items"> <div class="field__item"><a href="/blog/building-rest-endpoints-drupal-8" hreflang="en">Building REST Endpoints with Drupal 8 </a></div> <div class="field__item"><a href="/blog/creating-content-yaml-content-module" hreflang="en">Creating Content with YAML Content Module</a></div> <div class="field__item"><a href="/blog/mediacurrents-drupal-theme-generator" hreflang="en">Mediacurrent&#039;s Drupal Theme Generator</a></div> </div> </div> <div class="gatsby-iframe-container"><iframe class="gatsby-iframe" src="https://preview-misriptide.gtsb.io/blog/integrating-amazon-alexa-drupal-8-site"></iframe></div> Wed, 16 Aug 2017 12:31:04 +0000 Sam Seide 3043 at https://publish.mediacurrent.com