Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix BB-760 : When elasticsearch configuration is missing, server crashes #1081

Open
wants to merge 8 commits into
base: master
Choose a base branch
from

Conversation

Tarunmeena0901
Copy link
Contributor

Problem

BB-760

Solution

As the reason behind the crashing of BB server was the absence of elastic search configuration in our configuration template , I added some checks just before we are initializng the search server in app.js .
Those checks will ensure incase of missing configuration elastic search will still get some hardcoded configuration which will prevent it from crashing on initializing

and also incase of missing configuration error will be logged in console and a warning banner will be displayed on homepage

Screenshot 2024-03-28 001914

Screenshot 2024-03-28 001936

Areas of Impact

  • ./src/server/app.js
  • ./src/api/app.js

Copy link
Contributor

@MonkeyDo MonkeyDo left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Sorry for the long delay!
I have some suggestions to simplify the code a bit and deduplicate some code:

src/api/app.js Outdated Show resolved Hide resolved
src/server/app.js Outdated Show resolved Hide resolved

const searchConfig = config.search || {};
// Check if ElasticSearch configuration is provided
if (searchConfig.node && searchConfig.auth) {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Since this code is duplicated in api/app.js, it would make more sense to implement all this default config fallback code in search.init instead.

@@ -124,6 +139,24 @@ app.use((req, res, next) => {
});
}

if (!searchConfig.node || !searchConfig.auth) {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is going to be true even though search was initialized with a default configuration, no?
In that case the messages below could be misleading as search could be available with default config.

I propose we do something like for the auth setup and make search.init return a boolean if the connection is alive and false otherwise:

const authInitiated = auth.init(app);

Here's what the code could look like:

/**
 * Search init
 * @description Sets up the search server connection with defaults,
 * and returns a connection status boolean
 * @param {ORM} orm the BookBrainz ORM
 * @param {ClientOptions} [connectionSettings] Optional (but recommended) connection settings, will provide defaults if missing
 * @returns {Promise<boolean>} A Promise which resolves to the connection status boolean
 */
export async function init(orm, connectionSettings) {
	/* Fallback configuration code here */

	_client = new ElasticSearch.Client(connectionSettings);
	try {
		// check for connection
		await _client.ping();
	}
	catch (error) {
		// not connected
		return false;
	}
	const mainIndexExists = await _client.indices.exists({index: _index});
	if (!mainIndexExists) {
		// Automatically index on app startup if we haven't already, but don't block app setup
		generateIndex(orm).catch(log.error);
	}
	// connected
	return true;
}

With these imported types

import ElasticSearch, {type ClientOptions} from '@elastic/elasticsearch';
import {type ORM} from 'bookbrainz-data';

And finally in app.js you can do
const searchInitiated = await search.init(app.locals.orm, Object.assign({}, config.search));
and add an banner if searchInitiated is false

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Great solution! One thing I would like to ask: the type you mentioned here
{type ClientOptions} from '@elastic/elasticsearch'; doesn't have the properties that options should have like "auth" and "host"

options = {
	auth: { password: 'changeme', username: 'elastic' },
	node: 'http://localhost:9200',
	requestTimeout: 60000,
	host: 'localhost:9200'
};

Comment on lines 144 to 151
if (process.env.DEPLOY_ENV === 'test') {
msg = 'Elastic search configs are not provided. Search server is not available on the test website';
}
else if (process.env.DEPLOY_ENV === 'beta') {
msg = 'Elastic search configs are not provided. Search server is not available on the beta website';
}
else {
msg = 'Elastic search configs are not provided. Search server is not available in your local environment';
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think we can do a single message for all environments, maybe something like
'We could not connect to our search server, all search functionality is unavailable.'

@Tarunmeena0901
Copy link
Contributor Author

There were some unexpected es lint error not releated to the changes in this PR , but I fixed them too I hope it does no make things confusing for you

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
2 participants