Querying the Database from Angular

One of possible improvements is to perform queries against MongoDB directly from Angular Universal. In this lesson you will create a service which does this job.

MongoService#

Generating the service#

Start your work by generating a new service that will be used to connect to MongoDB:

To apply the Don't Repeat Yourself (DRY) principle, you will utilize this service in the api.ts file. In other words, you will move the database querying logic from api.ts to MongoService. A naive implementation could look like this:

The prepared class can now be imported into api.ts instead of the current MongoDB-related logic. Unfortunately, this is not trivial. Try to inject the prepared service anywhere in your application, such as ProductsService:

Now run the Angular compiler:

Take a look at the content of the dist/browser/main***.js bundle that is sent to the end user's browser:

That's a severe security breach: you disclose your database connection string to every user of your application!

Angular Universal is an excellent solution as it enables sharing the code base between browser and server bundles. While it's a great way to avoid duplicating business logic in your project, it might lead to serious security breaches and compromising sensitive data such as database connection strings!

Using the isPlatformBrowser() and isPlatformServer() methods doesn't help here because the same code base is still used on both platforms. This is how the isPlatformXXX() method used in I18nService is translated to a JavaScript bundle:

As you can see, the server-specific code branch is still present in the browser bundle.

Moreover, the connection string may change in the future. Do you want to rebuild your application because a variable value has changed? You probably don't.

Providing secrets to server-side Angular#

Fortunately, ngExpressEngine that we use to render Angular views can provide additional injection tokens to the Angular application. You could provide Angular with a connection string and use it to set up a database connection. However, that would lead you to another pitfall: a database connection would be set up every time a user accesses the application. Instead, it would be better to provide Angular with an already instantiated connection and inject it into MongoService using Dependency Injection.

First, let's export the dbClient object from api.ts:

Next, adjust the statement that imports from api.ts into server.ts:

 

This page is a preview of The newline Guide to Angular Universal

No discussions yet