puter-deploy / src /backend /src /CoreModule.js
gionuibk's picture
Upload folder using huggingface_hub
61d39e2 verified
/*
* Copyright (C) 2024-present Puter Technologies Inc.
*
* This file is part of Puter.
*
* Puter is free software: you can redistribute it and/or modify
* it under the terms of the GNU Affero General Public License as published
* by the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Affero General Public License for more details.
*
* You should have received a copy of the GNU Affero General Public License
* along with this program. If not, see <https://www.gnu.org/licenses/>.
*/
const { AdvancedBase } = require('@heyputer/putility');
const { NotificationES } = require('./om/entitystorage/NotificationES');
const { ProtectedAppES } = require('./om/entitystorage/ProtectedAppES');
const { Context } = require('./util/context');
const { LLOWrite } = require('./filesystem/ll_operations/ll_write');
const { LLRead } = require('./filesystem/ll_operations/ll_read');
const { RuntimeModule } = require('./extension/RuntimeModule.js');
const { TYPE_DIRECTORY, TYPE_FILE } = require('./filesystem/FSNodeContext.js');
const { TDetachable } = require('@heyputer/putility/src/traits/traits.js');
const { MultiDetachable } = require('@heyputer/putility/src/libs/listener.js');
const { OperationFrame } = require('./services/OperationTraceService');
/**
* @footgun - real install method is defined above
*/
const install = async ({ context, services, app, useapi, modapi }) => {
const config = require('./config');
// === LIBRARIES ===
useapi.withuse(() => {
def('Service', require('./services/BaseService'));
def('Module', AdvancedBase);
def('core.util.helpers', require('./helpers'));
def('core.util.permission', require('./services/auth/permissionUtils.mjs').PermissionUtil);
def('puter.middlewares.auth', require('./middleware/auth2'));
def('puter.middlewares.configurable_auth', require('./middleware/configurable_auth'));
def('puter.middlewares.anticsrf', require('./middleware/anticsrf'));
def('core.APIError', require('./api/APIError'));
def('core.Context', Context);
def('core', require('./services/auth/Actor'), { assign: true });
def('core', {
TDetachable,
MultiDetachable,
}, { assign: true });
def('core.config', config);
// Note: this is an incomplete export; it was added for a proprietary
// extension. Contributors may wish to add definitions in the 'fs.'
// scope. Needing to add these individually is possibly a symptom of an
// anti-pattern; "export filesystem operations to extensions" is one
// statement in English, so maybe it should be one statement of code.
def('core.fs', {
LLOWrite,
LLRead,
TYPE_DIRECTORY,
TYPE_FILE,
OperationFrame,
});
def('core.fs.selectors', require('./filesystem/node/selectors'));
def('core.util.stream', require('./util/streamutil'));
def('web', require('./util/expressutil'));
def('core.validation', require('./validation'));
def('core.database', require('./services/database/consts.js'));
// Add otelutil functions to `core.`
def('core.spanify', require('./util/otelutil').spanify);
def('core.abtest', require('./util/otelutil').abtest);
// Extension compatibility
const runtimeModule = new RuntimeModule({ name: 'core' });
context.get('runtime-modules').register(runtimeModule);
runtimeModule.exports = useapi.use('core');
});
modapi.libdir('core.util', './util');
// === SERVICES ===
// TODO: move these to top level imports or await imports and esm this file
const { CommandService } = require('./services/CommandService');
const { HTTPThumbnailService } = require('./services/thumbnails/HTTPThumbnailService');
const { PureJSThumbnailService } = require('./services/thumbnails/PureJSThumbnailService');
const { NAPIThumbnailService } = require('./services/thumbnails/NAPIThumbnailService');
const { RateLimitService } = require('./services/sla/RateLimitService');
const { AuthService } = require('./services/auth/AuthService');
const { SLAService } = require('./services/sla/SLAService');
const { PermissionService } = require('./services/auth/PermissionService');
const { ACLService } = require('./services/auth/ACLService');
const { CoercionService } = require('./services/drivers/CoercionService');
const { PuterSiteService } = require('./services/PuterSiteService');
const { ContextInitService } = require('./services/ContextInitService');
const { IdentificationService } = require('./services/abuse-prevention/IdentificationService');
const { AuthAuditService } = require('./services/abuse-prevention/AuthAuditService');
const { RegistryService } = require('./services/RegistryService');
const { RegistrantService } = require('./services/RegistrantService');
const { SystemValidationService } = require('./services/SystemValidationService');
const { EntityStoreService } = require('./services/EntityStoreService');
const SQLES = require('./om/entitystorage/SQLES');
const ValidationES = require('./om/entitystorage/ValidationES');
const { SetOwnerES } = require('./om/entitystorage/SetOwnerES');
const AppES = require('./om/entitystorage/AppES');
const WriteByOwnerOnlyES = require('./om/entitystorage/WriteByOwnerOnlyES');
const SubdomainES = require('./om/entitystorage/SubdomainES');
const { MaxLimitES } = require('./om/entitystorage/MaxLimitES');
const { AppLimitedES } = require('./om/entitystorage/AppLimitedES');
const { ReadOnlyES } = require('./om/entitystorage/ReadOnlyES');
const { OwnerLimitedES } = require('./om/entitystorage/OwnerLimitedES');
const { ESBuilder } = require('./om/entitystorage/ESBuilder');
const { Eq, Or } = require('./om/query/query');
const { MakeProdDebuggingLessAwfulService } = require('./services/MakeProdDebuggingLessAwfulService');
const { ConfigurableCountingService } = require('./services/ConfigurableCountingService');
const { FSLockService } = require('./services/fs/FSLockService');
const { StrategizedService } = require('./services/StrategizedService');
const FilesystemAPIService = require('./services/FilesystemAPIService');
const ServeGUIService = require('./services/ServeGUIService');
const PuterAPIService = require('./services/PuterAPIService');
const { RefreshAssociationsService } = require('./services/RefreshAssociationsService');
// Service names beginning with '__' aren't called by other services;
// these provide data/functionality to other services or produce
// side-effects from the events of other services.
// === Services which extend BaseService ===
services.registerService('system-validation', SystemValidationService);
services.registerService('commands', CommandService);
services.registerService('__api-filesystem', FilesystemAPIService);
services.registerService('__api', PuterAPIService);
services.registerService('__gui', ServeGUIService);
services.registerService('registry', RegistryService);
services.registerService('__registrant', RegistrantService);
services.registerService('fslock', FSLockService);
services.registerService('es:app', EntityStoreService, {
entity: 'app',
upstream: ESBuilder.create([
SQLES, { table: 'app', debug: true },
AppES,
AppLimitedES, {
permission_prefix: 'apps-of-user',
// When apps query es:apps, they're allowed to see apps which
// are approved for listing and they're allowed to see their
// own entry.
exception: async () => {
const actor = Context.get('actor');
return new Or({
children: [
new Eq({
key: 'approved_for_listing',
value: 1,
}),
new Eq({
key: 'uid',
value: actor.type.app.uid,
}),
],
});
},
},
WriteByOwnerOnlyES,
ValidationES,
SetOwnerES,
ProtectedAppES,
MaxLimitES, { max: 5000 },
]),
});
const { EntriService } = require('./services/EntriService.js');
services.registerService('entri-service', EntriService);
const { InformationService } = require('./services/information/InformationService');
services.registerService('information', InformationService);
const { TraceService } = require('./services/TraceService.js');
services.registerService('traceService', TraceService);
const { FilesystemService } = require('./filesystem/FilesystemService');
services.registerService('filesystem', FilesystemService);
services.registerService('es:subdomain', EntityStoreService, {
entity: 'subdomain',
upstream: ESBuilder.create([
SQLES, { table: 'subdomains', debug: true },
SubdomainES,
AppLimitedES, { permission_prefix: 'subdomains-of-user' },
WriteByOwnerOnlyES,
ValidationES,
SetOwnerES,
MaxLimitES, { max: 5000 },
]),
});
services.registerService('es:notification', EntityStoreService, {
entity: 'notification',
upstream: ESBuilder.create([
SQLES, { table: 'notification', debug: true },
NotificationES,
OwnerLimitedES,
ReadOnlyES,
SetOwnerES,
MaxLimitES, { max: 200 },
]),
});
services.registerService('rate-limit', RateLimitService);
services.registerService('auth', AuthService);
// services.registerService('preauth', PreAuthService);
services.registerService('permission', PermissionService);
services.registerService('sla', SLAService);
services.registerService('acl', ACLService);
services.registerService('coercion', CoercionService);
services.registerService('puter-site', PuterSiteService);
services.registerService('context-init', ContextInitService);
services.registerService('identification', IdentificationService);
services.registerService('auth-audit', AuthAuditService);
services.registerService('counting', ConfigurableCountingService);
services.registerService('thumbnails', StrategizedService, {
strategy_key: 'engine',
default_strategy: 'purejs',
strategies: {
napi: [NAPIThumbnailService],
purejs: [PureJSThumbnailService],
http: [HTTPThumbnailService],
},
});
services.registerService('__refresh-assocs', RefreshAssociationsService);
services.registerService('__prod-debugging', MakeProdDebuggingLessAwfulService);
const { EventService } = require('./services/EventService');
services.registerService('event', EventService);
const { PuterVersionService } = require('./services/PuterVersionService');
services.registerService('puter-version', PuterVersionService);
const { SessionService } = require('./services/SessionService');
services.registerService('session', SessionService);
const { EdgeRateLimitService } = require('./services/abuse-prevention/EdgeRateLimitService');
services.registerService('edge-rate-limit', EdgeRateLimitService);
const { CleanEmailService } = require('./services/CleanEmailService');
services.registerService('clean-email', CleanEmailService);
const { Emailservice } = require('./services/EmailService');
services.registerService('email', Emailservice);
const { TokenService } = require('./services/auth/TokenService');
services.registerService('token', TokenService);
const { OTPService } = require('./services/auth/OTPService');
services.registerService('otp', OTPService);
const { UserProtectedEndpointsService } = require('./services/web/UserProtectedEndpointsService');
services.registerService('__user-protected-endpoints', UserProtectedEndpointsService);
const { AntiCSRFService } = require('./services/auth/AntiCSRFService');
services.registerService('anti-csrf', AntiCSRFService);
const { LockService } = require('./services/LockService');
services.registerService('lock', LockService);
const { PuterHomepageService } = require('./services/PuterHomepageService');
services.registerService('puter-homepage', PuterHomepageService);
const { GetUserService } = require('./services/GetUserService');
services.registerService('get-user', GetUserService);
const { DetailProviderService } = require('./services/DetailProviderService');
services.registerService('whoami', DetailProviderService);
const { DriverService } = require('./services/drivers/DriverService');
services.registerService('driver', DriverService);
const { ScriptService } = require('./services/ScriptService');
services.registerService('script', ScriptService);
const { NotificationService } = require('./services/NotificationService');
services.registerService('notification', NotificationService);
const { ShareService } = require('./services/ShareService');
services.registerService('share', ShareService);
const { GroupService } = require('./services/auth/GroupService');
services.registerService('group', GroupService);
const { VirtualGroupService } = require('./services/auth/VirtualGroupService');
services.registerService('virtual-group', VirtualGroupService);
const { PermissionAPIService } = require('./services/PermissionAPIService');
services.registerService('__permission-api', PermissionAPIService);
const { AnomalyService } = require('./services/AnomalyService');
services.registerService('anomaly', AnomalyService);
const { HelloWorldService } = require('./services/HelloWorldService');
services.registerService('hello-world', HelloWorldService);
const { SystemDataService } = require('./services/SystemDataService');
services.registerService('system-data', SystemDataService);
const { SUService } = require('./services/SUService');
services.registerService('su', SUService);
const { ShutdownService } = require('./services/ShutdownService');
services.registerService('shutdown', ShutdownService);
const { BootScriptService } = require('./services/BootScriptService');
services.registerService('boot-script', BootScriptService);
const { FeatureFlagService } = require('./services/FeatureFlagService');
services.registerService('feature-flag', FeatureFlagService);
const { KernelInfoService } = require('./services/KernelInfoService');
services.registerService('kernel-info', KernelInfoService);
const { DriverUsagePolicyService } = require('./services/drivers/DriverUsagePolicyService');
services.registerService('driver-usage-policy', DriverUsagePolicyService);
const { ReferralCodeService } = require('./services/ReferralCodeService');
services.registerService('referral-code', ReferralCodeService);
const { VerifiedGroupService } = require('./services/VerifiedGroupService');
services.registerService('__verified-group', VerifiedGroupService);
const { UserService } = require('./services/UserService');
services.registerService('user', UserService);
const { WSPushService } = require('./services/WSPushService');
services.registerService('__event-push-ws', WSPushService);
const { SNSService } = require('./services/SNSService');
services.registerService('sns', SNSService);
const { WispService } = require('./services/WispService');
services.registerService('wisp', WispService);
// const { AWSSecretsPopulator } = require('./services/AWSSecretsPopulator.js');
// services.registerService('awsthing', AWSSecretsPopulator);
const { WebDavFS } = require('./services/WebDAV/WebDAVService.js');
services.registerService('dav', WebDavFS);
const { RequestMeasureService } = require('./services/RequestMeasureService');
services.registerService('request-measure', RequestMeasureService);
const { ChatAPIService } = require('./services/ChatAPIService');
services.registerService('__chat-api', ChatAPIService);
const { WorkerService } = require('./services/worker/WorkerService');
services.registerService('worker-service', WorkerService);
const { MeteringServiceWrapper } = require('./services/MeteringService/MeteringServiceWrapper.mjs');
services.registerService('meteringService', MeteringServiceWrapper);
const { PermissionShortcutService } = require('./services/auth/PermissionShortcutService');
services.registerService('permission-shortcut', PermissionShortcutService);
const { FileCacheService } = require('./services/file-cache/FileCacheService');
services.registerService('file-cache', FileCacheService);
};
const install_legacy = async ({ services }) => {
const { OperationTraceService } = require('./services/OperationTraceService');
const { ClientOperationService } = require('./services/ClientOperationService');
const { EngPortalService } = require('./services/EngPortalService');
// === Services which do not yet extend BaseService ===
// services.registerService('filesystem', FilesystemService);
services.registerService('operationTrace', OperationTraceService);
services.registerService('client-operation', ClientOperationService);
services.registerService('engineering-portal', EngPortalService);
};
/**
* Core module for the Puter platform that includes essential services including
* authentication, filesystems, rate limiting, permissions, and various API endpoints.
*
* This is a monolithic module. Incrementally, services should be migrated to
* Core2Module and other modules instead. Core2Module has a smaller scope, and each
* new module will be a cohesive concern. Once CoreModule is empty, it will be removed
* and Core2Module will take on its name.
*/
class CoreModule extends AdvancedBase {
dirname () {
return __dirname;
}
async install (context) {
const services = context.get('services');
const app = context.get('app');
const useapi = context.get('useapi');
const modapi = context.get('modapi');
await install({ context, services, app, useapi, modapi });
}
/**
* Installs legacy services that don't extend BaseService and require special handling.
* These services were created before the BaseService class existed and don't listen
* to the init event. They need to be installed after the init event is dispatched
* due to initialization order dependencies.
*
* @param {Object} context - The context object containing service references
* @param {Object} context.services - Service registry for registering legacy services
* @returns {Promise<void>} Resolves when legacy services are installed
*/
async install_legacy (context) {
const services = context.get('services');
await install_legacy({ services });
}
}
module.exports = CoreModule;