routes/apiHandlers.js
/**
 * Create the account on the blockchain using steem-js
 * Send the data to the conveyor that will store the user account
 * Remove the user information from our database
 */
Create the account on the blockchain using steem-js
Send the data to the conveyor that will store the user account
Remove the user information from our database
Create the account on the blockchain using steem - js Send the data to the conveyor that will store the user account Remove the user information from our database
async function handleCreateAccount(req) {
    if (process.env.REACT_DISABLE_ACCOUNT_CREATION === 'true') {
        throw new ApiError({
            type: 'Account creation temporarily disabled',
            status: 503,
        });
    }
    const { username, public_keys, token, email } = req.body; 
    const decoded = verifyToken(token, 'create_account');
    if (!username) {
        throw new ApiError({ type: 'error_api_username_required' });
    }
    try {
        accountNameIsValid(username);
    } catch (e) {
        throw new ApiError({
            type: e.message,
        });
    }
    if (!public_keys) {
        throw new ApiError({ type: 'error_api_public_keys_required' });
    }
    if (!email) {
        throw new ApiError({ type: 'error_api_email_required' });
    }
    const user = await database.findUser({
        where: { email: decoded.email },
    });
    if (!user) {
        throw new ApiError({ type: 'error_api_user_exists_not' });
    }
    if (user.status !== 'approved') {
        throw new ApiError({
            type: 'error_api_account_verification_pending',
        });
    }
    const creationHash = hash.sha256(crypto.randomBytes(32)).toString('hex');
    await database.updateUsers(
        {
            creation_hash: creationHash,
        },
        {
            where: {
                email: decoded.email,
                creation_hash: null,
            },
        }
    );
    const weightThreshold = 1;
    const accountAuths = [];
    const publicKeys = JSON.parse(public_keys);
    const metadata = '{}';
    const owner = {
        weight_threshold: weightThreshold,
        account_auths: accountAuths,
        key_auths: [[publicKeys.owner, 1]],
    };
    const active = {
        weight_threshold: weightThreshold,
        account_auths: accountAuths,
        key_auths: [[publicKeys.active, 1]],
    };
    const posting = {
        weight_threshold: weightThreshold,
        account_auths: accountAuths,
        key_auths: [[publicKeys.posting, 1]],
    };
    const [activeCreationHash] = await database.query(
        'SELECT SQL_NO_CACHE creation_hash FROM users WHERE email = ?',
        {
            replacements: [decoded.email],
            type: database.Sequelize.QueryTypes.SELECT,
        }
    );
    if (
        !activeCreationHash ||
        activeCreationHash.creation_hash !== creationHash
    ) {
        throw new ApiError({ type: 'error_api_account_creation_progress' });
    }
    try {
        await services.createAccount({
            active,
            memo_key: publicKeys.memo,
            json_metadata: metadata,
            owner,
            posting,
            new_account_name: username,
        });
    } catch (cause) {
        await database.updateUsers(
            {
                creation_hash: null,
            },
            { where: { email: decoded.email } }
        );
        cause.message = cause.message.split('\n').slice(0, 2);
        throw new ApiError({
            type: 'error_api_create_account',
            cause,
            status: 500,
        });
    }
    await database.updateUsers(
        {
            status: 'created',
        },
        { where: { email: decoded.email } }
    );
    try {
        await services.gatekeeperMarkSignupCreated(user);
    } catch (error) {
        logger.warn({ error }, 'gatekeeper.signup_mark_created failed');
    }
    const params = [
        username,
        {
            phone: user.phone_number.replace(/[^+0-9]+/g, ''),
            email: user.email,
        },
    ];
    services.conveyorCall('set_user_data', params).catch(error => {
        req.log.warn(
            error,
            'Unable to store user data in conveyor... retrying'
        );
        setTimeout(() => {
            services.conveyorCall('set_user_data', params).catch(error => {
                req.log.error(error, 'Unable to store user data in conveyor');
            });
        }, 5 * 1000);
    });
    services
        .condenserTransfer(email, username, publicKeys.owner)
        .catch(error => {
            req.log.error(error, 'Unable to send recovery info to condenser');
        });
    return { success: true };
}
async function handleCreateAccount ( req ) { if ( process . env . REACT_DISABLE_ACCOUNT_CREATION === 'true' ) { throw new ApiError ( { type : 'Account creation temporarily disabled' , status : 503 , } ) ; } const { username , public_keys , token , email } = req . body ; const decoded = verifyToken ( token , 'create_account' ) ; if ( ! username ) { throw new ApiError ( { type : 'error_api_username_required' } ) ; } try { accountNameIsValid ( username ) ; } catch ( e ) { throw new ApiError ( { type : e . message , } ) ; } if ( ! public_keys ) { throw new ApiError ( { type : 'error_api_public_keys_required' } ) ; } if ( ! email ) { throw new ApiError ( { type : 'error_api_email_required' } ) ; } const user = await database . findUser ( { where : { email : decoded . email } , } ) ; if ( ! user ) { throw new ApiError ( { type : 'error_api_user_exists_not' } ) ; } if ( user . status !== 'approved' ) { throw new ApiError ( { type : 'error_api_account_verification_pending' , } ) ; } const creationHash = hash . sha256 ( crypto . randomBytes ( 32 ) ) . toString ( 'hex' ) ; await database . updateUsers ( { creation_hash : creationHash , } , { where : { email : decoded . email , creation_hash : null , } , } ) ; const weightThreshold = 1 ; const accountAuths = [ ] ; const publicKeys = JSON . parse ( public_keys ) ; const metadata = '{}' ; const owner = { weight_threshold : weightThreshold , account_auths : accountAuths , key_auths : [ [ publicKeys . owner , 1 ] ] , } ; const active = { weight_threshold : weightThreshold , account_auths : accountAuths , key_auths : [ [ publicKeys . active , 1 ] ] , } ; const posting = { weight_threshold : weightThreshold , account_auths : accountAuths , key_auths : [ [ publicKeys . posting , 1 ] ] , } ; const [ activeCreationHash ] = await database . query ( 'SELECT SQL_NO_CACHE creation_hash FROM users WHERE email = ?' , { replacements : [ decoded . email ] , type : database . Sequelize . QueryTypes . SELECT , } ) ; if ( ! activeCreationHash || activeCreationHash . creation_hash !== creationHash ) { throw new ApiError ( { type : 'error_api_account_creation_progress' } ) ; } try { await services . createAccount ( { active , memo_key : publicKeys . memo , json_metadata : metadata , owner , posting , new_account_name : username , } ) ; } catch ( cause ) { await database . updateUsers ( { creation_hash : null , } , { where : { email : decoded . email } } ) ; cause . message = cause . message . split ( '\n' ) . slice ( 0 , 2 ) ; throw new ApiError ( { type : 'error_api_create_account' , cause , status : 500 , } ) ; } await database . updateUsers ( { status : 'created' , } , { where : { email : decoded . email } } ) ; try { await services . gatekeeperMarkSignupCreated ( user ) ; } catch ( error ) { logger . warn ( { error } , 'gatekeeper.signup_mark_created failed' ) ; } const params = [ username , { phone : user . phone_number . replace ( / [^+0-9]+ / g , '' ) , email : user . email , } , ] ; services . conveyorCall ( 'set_user_data' , params ) . catch ( error => { req . log . warn ( error , 'Unable to store user data in conveyor... retrying' ) ; setTimeout ( ( ) => { services . conveyorCall ( 'set_user_data' , params ) . catch ( error => { req . log . error ( error , 'Unable to store user data in conveyor' ) ; } ) ; } , 5 * 1000 ) ; } ) ; services . condenserTransfer ( email , username , publicKeys . owner ) . catch ( error => { req . log . error ( error , 'Unable to send recovery info to condenser' ) ; } ) ; return { success : true } ; }
Create the account on the blockchain using steem-js
 Send the data to the conveyor that will store the user account
 Remove the user information from our database
Create the account on the blockchain using steem - js Send the data to the conveyor that will store the user account Remove the user information from our database
// Do not allow account creations if REACT_DISABLE_ACCOUNT_CREATION is set to true // eslint-disable-line camelcase // eslint-disable-line camelcase // steem-js error messages are so long that the log is clipped causing // errors in scalyr parsing // TODO: this should retry more than once // eslint-disable-next-line // Post to Condenser's account recovery endpoint.