export const google_login = [
    {
        id: 'googleCodeLambda',
        name: 'Google Code Lambda',
        method: 'GET',
        description: '',
        route: '/v3/api/custom/lambda/google/code',
        inputs: [
          { id: 'state', key: 'state', value: '', valueType: 'String', parent: 'query' }
        ],
        response: [
            { id: "error", key: 'error', value: "false", valueType: 'Boolean', parent: '' },
            { id: "message", key: 'message', value: 'OK', valueType: 'String', parent: '' }
        ],
        code: `app.get("/v3/api/custom/lambda/google/code", [UrlMiddleware], async function (req, res) {
          try {
            const parts = req.query.state.split("~");
            const base64DecodeBuffer = new Buffer.from(parts[0], "base64");
            let base64Decode = base64DecodeBuffer.toString("ascii").split(":");
            const projectId = base64Decode[0];
            const role = parts[1];
            let needRefreshToken = false;
            let refreshToken = undefined;
      
            if (req.query.state.includes('with_refresh')) {
              needRefreshToken = true;
            }
      
            // Note: Checking for permission as we can't use PermissionMiddleware here
      
            const database = base64Decode[2]?? config.databaseName;
      
            let sdk = new BackendSDK();
            sdk.setDatabase(database);
            sdk.setProjectId(projectId);
      
      
            let manaknightSDK = new ManaKnightSDK();
      
      
            manaknightSDK.getDatabase();
            manaknightSDK.setProjectId(projectId);
      
            let originalUrl = req.originalUrl;
      
            manaknightSDK.getDatabase();
            manaknightSDK.setProjectId(projectId);
            const svc = new permissionService(sdk, projectId, req.header);
            let validate = await svc.validate(originalUrl);
            if (validate.error) {
              return res.status(401).json({ message: validate.message });
            }
            let project = {};
            if (config.env == "production") {
               project = require("../../../project");
              
            } else {
              manaknightSDK.setProjectId("manaknight");
              manaknightSDK.setTable("projects");
        
               project = (await manaknightSDK.get({
                project_id: projectId
              }))[0];
      
            }
      
            const googleConfig = {
              clientID: config.google.client_id,
              clientSecret: config.google.client_secret,
              redirectURL: config.google.redirect_url,
              defaultScope: ["https://www.googleapis.com/auth/userinfo.email", "https://www.googleapis.com/auth/userinfo.profile"]
            };
      
            const googleLogin = new NodeGoogleLogin(googleConfig);
      
            const userProfile = await googleLogin.getUserProfile(req.query.code);
            let service = new AuthService();
            logService.log(userProfile);
            //verify if that user belongs to that company
            // check if parts has third item
            let id;
            if (parts[2]) {
              const company_id = parts[2];
              sdk.setProjectId(projectId);
              sdk.setTable("company");
              const company = await sdk.get({ id: company_id });
              if (!company) {
                return res.status(404).json({ message: "Company Not found", error: true });
              }
              id = await service.googleLogin(sdk, projectId, userProfile.user, userProfile.tokens, role, company_id);
            } else {
              id = await service.googleLogin(sdk, projectId, userProfile.user, userProfile.tokens, role);
            }
      
            if (typeof id == "string") {
              return res.status(403).json({
                error: true,
                message: id
              });
            }
      
            if (needRefreshToken) {
              refreshToken = JwtService.createAccessToken(
                {
                  user_id: id,
                  role: role
                },
                config.refresh_jwt_expire,
                config.jwt_key
              );
              let expireDate = new Date();
              expireDate.setSeconds(expireDate.getSeconds() + config.refresh_jwt_expire);
              await service.saveRefreshToken(sdk, req.projectId, id, refreshToken, expireDate);
      
            }
      
            const data = JSON.stringify({
              error: false,
              role: role,
              token: JwtService.createAccessToken(
                {
                  user_id: id,
                  role: role
                },
                config.jwt_expire,
                config.jwt_key
              ),
              expire_at: config.jwt_expire,
              user_id: id,
              refresh_token: refreshToken,
            });
      
            const encodedURI = encodeURI(data);
      
            res.redirect(\`https://\${project.hostname}/login/oauth?data=\${encodedURI}\`);
          } catch (error) {
            console.log(error);
            return res.status(403).json({
              error: true,
              message: "Invalid Credentials"
            });
          }
        });`,
        doc: '',
        unit: '',
        protected: false,
        authorizedRoles: [],
        imports: '',
        type: 'lambda',
        group: 'google_login'
      },
      {
        id: 'googleCodeMobile',
        name: 'Google Code Mobile',
        method: 'GET',
        description: 'Endpoint to handle mobile app Google login via code exchange.',
        route: '/v3/api/custom/lambda/google/code/mobile',
        inputs: [
          { id: 'role', name: 'role', type: 'query', rules: 'optional', dataType: 'String', value: 'user' },
          { id: 'is_refresh', name: 'is_refresh', type: 'query', rules: 'optional', dataType: 'Boolean', value: 'false' },
          { id: 'code', name: 'code', type: 'query', rules: 'required', dataType: 'String', value: '' }
        ],
        response: [
            { id: "error", key: 'error', value: "false", valueType: 'Boolean', parent: '' },
            { id: "message", key: 'message', value: '', valueType: 'String', parent: '' },
            { id: "role", key: 'role', value: '', valueType: 'String', parent: '' },
            { id: "token", key: 'token', value: '', valueType: 'String', parent: '' },
            { id: "expire_at", key: 'expire_at', value: '', valueType: 'String', parent: '' },
            { id: "user_id", key: 'user_id', value: '', valueType: 'Number', parent: '' },
            { id: "refrsh_token", key: 'refresh_token', value: '', valueType: 'String', parent: '' },
        ],
        code: `app.get("/v3/api/custom/lambda/google/code/mobile", middlewares, async function (req, res) {
          const projectId = req.projectId;
          const role = req.query.role ?? "user";
          const needRefreshToken = req.query.is_refresh ?? false;
          let refreshToken = undefined;
      
          const googleConfig = {
            clientID: config.google.client_id,
            clientSecret: config.google.client_secret,
            redirectURL: config.google.redirect_url,
            defaultScope: ["https://www.googleapis.com/auth/userinfo.email", "https://www.googleapis.com/auth/userinfo.profile"]
          };
      
          let sdk = req.sdk;
      
          const googleLogin = new NodeGoogleLogin(googleConfig);
      
          try {
            const userProfile = await googleLogin.getUserProfile(req.query.code);
            let service = new AuthService();
            logService.log(userProfile);
      
            let id;
            if (parts[2]) {
              const company_id = parts[2];
              sdk.setProjectId(projectId);
              sdk.setTable("company");
              const company = await sdk.get({ id: company_id });
              if (!company) {
                return res.status(404).json({ message: "Company Not found", error: true });
              }
              id = await service.googleLogin(sdk, projectId, userProfile.user, userProfile.tokens, role, company_id);
            } else {
              id = await service.googleLogin(sdk, projectId, userProfile.user, userProfile.tokens, role);
            }
      
            if (typeof id == "string") {
              return res.status(403).json({
                error: true,
                message: id
              });
            }
      
            if (needRefreshToken) {
              refreshToken = JwtService.createAccessToken(
                {
                  user_id: id,
                  role: role
                },
                config.refresh_jwt_expire,
                config.jwt_key
              );
              let expireDate = new Date();
              expireDate.setSeconds(expireDate.getSeconds() + config.refresh_jwt_expire);
              await service.saveRefreshToken(sdk, req.projectId, id, refreshToken, expireDate);
      
            }
      
            return res.status(200).json({
              error: false,
              role: role,
              token: JwtService.createAccessToken(
                {
                  user_id: id,
                  role: role
                },
                config.jwt_expire,
                config.jwt_key
              ),
              expire_at: config.jwt_expire,
              user_id: id,
              refresh_token: refreshToken,
            });
          } catch (error) {
            console.log(error);
            return res.status(403).json({
              error: true,
              message: "Invalid Credentials"
            });
          }
        });`,
        doc: '',
        unit: '',
        protected: false,
        authorizedRoles: [],
        imports: '',
        type: 'lambda',
        group: 'google_login'
      },
      {
        id: 'googleLoginLambda',
        name: 'Google Login Lambda',
        method: 'GET',
        description: 'Endpoint to generate Google login URL for user registration.',
        route: '/v3/api/custom/lambda/google/login',
        inputs: [
          { id: 'role', name: 'role', type: 'query', rules: 'required', dataType: 'String', value: '' },
          { id: 'company_id', name: 'company_id', type: 'query', rules: 'optional', dataType: 'String', value: '' },
          { id: 'is_refresh', name: 'is_refresh', type: 'query', rules: 'optional', dataType: 'Boolean', value: '' }
        ],
        response: [],
        code: `app.get("/v3/api/custom/lambda/google/login", middlewares, async function (req, res) {
          if (req.query.role === "admin") return res.status(403).json({ error: true, message: "Can't register admin with this API" });
      
          const googleConfig = {
            clientID: config.google.client_id,
            clientSecret: config.google.client_secret,
            redirectURL: config.google.redirect_url,
            defaultScope: ["https://www.googleapis.com/auth/userinfo.email", "https://www.googleapis.com/auth/userinfo.profile"]
          };
          const googleLogin = new NodeGoogleLogin(googleConfig);
      
          let authURL = googleLogin.generateAuthUrl() + "&state=" + req.headers["x-project"] + "~" + req.query.role 
          if (req.query.company_id != undefined) {
            authURL += "~" + req.query.company_id;
          }
          if (req.query.is_refresh != undefined) {
            authURL += "~" + "with_refresh";
          }
      
          logService.log(authURL);
      
          return res.send(authURL);
        });`,
        doc: '',
        unit: '',
        protected: false,
        authorizedRoles: [],
        imports: '',
        type: 'lambda',
        group: 'google_login'
      }
      
      
      
]

export const googleLoginImports = `
const AuthService = require("../../../services/AuthService");
const JwtService = require("../../../services/JwtService");
const ProjectMiddleware = require("../../../middleware/ProjectMiddleware");
const UrlMiddleware = require("../../../middleware/UrlMiddleware");
const HostMiddleware = require("../../../middleware/HostMiddleware");
const PermissionMiddleware = require("../../../middleware/PermissionMiddleware");
const permissionService = require("../../../services/PermissionService");
const DevLogService = require("../../../services/DevLogService");
const config = require("../../../config");
const NodeGoogleLogin = require("node-google-login");
const ManaKnightSDK = require("../../../core/ManaKnightSDK");
const BackendSDK = require("../../../core/BackendSDK");
const { ideahub_v1alpha } = require("googleapis");

const middlewares = [
  ProjectMiddleware,
  UrlMiddleware,
  HostMiddleware,
  PermissionMiddleware
  // RateLimitMiddleware,
  // LogMiddleware,
  // UsageMiddleware
  // CheckProjectMiddleware,
  // AnalyticMiddleware,
  // RoleMiddleware
];

let logService = new DevLogService();
`