Getting started with Contentful and Angular

Posted by James on September 7, 2019

I cut my teeth developing Drupal sites. I've got to say, I miss the open source vibe of the Drupal Cons and Camps. But it seems like the world has moved on, and you can knock something out with a mixture of Angular and Contentful pretty quickly.

At the moment this site is pretty straightforward. I'm using the content list endpoint to get the listings page, then the individual item lookup for the individual article pages. My Angular http service get function looks like this:

getContentItemByUrl(search) {  const path = `/spaces/{space}/environments/master/entries?access_token={accessToken}&content_type=story&fields.url=${search}`;  const url =  'https://cdn.contentful.com' + path;  return this.http.get(url, this.createHeaders());}

The Loop

WordPress developers might already be familiar with The Loop, which is a big while loop that looks for posts to display on the aggregator page of your site. The approach I've taken to headless CMS display is similar, only instead of looping through the list of posts we're looping through the content object.

The object returned from the getContentItemByUrl function looks like this:

"items": [        {            ...            "fields": {                "title": "Getting your Angular Universal site production ready",                "summary": "Want a quicker time to first paint...",                "bodyText": {                    "nodeType": "document",                    "data": {},                    "content": [                        {                            "nodeType": "paragraph",                            "content": [                                {                                    "nodeType": "text",                                    "value": "I've recently finished converting...",                                    "marks": [],                                    "data": {}                                }                            ],                        },                    ],                },            },        },    ]

You'll probably see that the content itself is quite heavily nested. Each paragraph is its own property within the object, and has a type, and associated markup and data. We want to loop through it, and based on each paragraph's type property, assign the data to a new component.

I've created an article component in my application. The component uses the getContentItemByUrl from the content service, then executes a switch statement on the results

for (const paragraph of content.fields.bodyText.content) {  switch (paragraph.nodeType) {    case 'paragraph':      ... deal with the paragraph  }}