{"version":3,"file":"index.mjs","names":[],"sources":["../../../src/modules/collector/index.ts"],"sourcesContent":["import type {\n    Argument,\n    ImportDeclaration,\n    Program,\n    VariableDeclaration,\n} from \"oxc-parser\";\n\nimport type { Specifier } from \"#/@types/specifier\";\nimport type { CompilerContext } from \"#/contexts/compiler\";\n\nimport { Visitor } from \"oxc-parser\";\n\nimport { CompileError } from \"#/errors/compile\";\n\n/**\n * Options for the `collect` function.\n */\ntype CollectOptions = {\n    /**\n     * Compiler context.\n     */\n    context: CompilerContext;\n    /**\n     * Program to be collected.\n     */\n    program: Program;\n    /**\n     * Package name of the CSS-in-JS package.\n     */\n    packageName: string;\n    /**\n     * CSS-in-JS package functions to be preprocessed.\n     */\n    includedFunctions: readonly string[];\n};\n\n/**\n * Result of the `collect` function.\n */\ntype CollectResult = {\n    /**\n     * Whether the CSS-in-JS package is imported.\n     */\n    isImported: boolean;\n    /**\n     * Namespaces used by the CSS-in-JS package.\n     */\n    namespaces: string[];\n    /**\n     * Specifiers used by the CSS-in-JS package.\n     */\n    specifiers: Specifier[];\n};\n\n/**\n * Collect the information of the file.\n */\nconst collect = (options: CollectOptions): CollectResult => {\n    const result: Program = options.program;\n\n    let isImported: boolean = false;\n    const namespaces: string[] = [];\n    const specifiers: Specifier[] = [];\n\n    const visitor: Visitor = new Visitor({\n        // ESM\n        ImportDeclaration: (node: ImportDeclaration): void => {\n            if (node.source.value !== options.packageName) return void 0;\n\n            isImported = true;\n\n            for (const specifier of node.specifiers) {\n                // import x from \"p\";\n                if (specifier.type === \"ImportDefaultSpecifier\") {\n                    namespaces.push(specifier.local.name);\n                }\n\n                // import * as x from \"p\";\n                else if (specifier.type === \"ImportNamespaceSpecifier\") {\n                    namespaces.push(specifier.local.name);\n                }\n\n                // import { x } from \"p\";\n                // import { x as y } from \"p\";\n                else if (specifier.type === \"ImportSpecifier\") {\n                    if (specifier.imported.type === \"Identifier\") {\n                        if (\n                            !options.includedFunctions.includes(\n                                specifier.imported.name,\n                            )\n                        )\n                            continue;\n\n                        specifiers.push({\n                            imported: specifier.imported.name,\n                            local: specifier.local.name,\n                        });\n                    }\n\n                    // unsupported type\n                    else {\n                        throw new CompileError({\n                            context: options.context,\n                            span: {\n                                start: specifier.imported.start,\n                                end: specifier.imported.end,\n                            },\n                            message: `Unsupported specifier imported type: ${specifier.imported.type}`,\n                        });\n                    }\n                }\n            }\n        },\n        // CJS\n        VariableDeclaration: (node: VariableDeclaration): void => {\n            for (const decl of node.declarations) {\n                if (!decl.init) continue;\n                if (decl.init.type !== \"CallExpression\") continue;\n                if (decl.init.callee.type !== \"Identifier\") continue;\n                if (decl.init.callee.name !== \"require\") continue;\n                if (decl.init.arguments.length !== 1) continue;\n\n                const arg: Argument | undefined = decl.init.arguments[0];\n\n                if (!arg) continue;\n                if (arg.type !== \"Literal\") continue;\n                if (arg.value !== options.packageName) continue;\n\n                isImported = true;\n\n                // const x = require(\"p\");\n                if (decl.id.type === \"Identifier\") {\n                    namespaces.push(decl.id.name);\n                }\n\n                // const { ... } = require(\"p\");\n                else if (decl.id.type === \"ObjectPattern\") {\n                    for (const prop of decl.id.properties) {\n                        // const { x } = require(\"p\");\n                        // const { x: y } = require(\"p\");\n                        if (prop.type === \"Property\") {\n                            if (prop.key.type !== \"Identifier\") {\n                                throw new CompileError({\n                                    context: options.context,\n                                    span: {\n                                        start: prop.key.start,\n                                        end: prop.key.end,\n                                    },\n                                    message: `Unsupported require property key type: ${prop.key.type}`,\n                                });\n                            }\n\n                            if (prop.value.type !== \"Identifier\") {\n                                throw new CompileError({\n                                    context: options.context,\n                                    span: {\n                                        start: prop.value.start,\n                                        end: prop.value.end,\n                                    },\n                                    message: `Unsupported require property value type: ${prop.value.type}`,\n                                });\n                            }\n\n                            specifiers.push({\n                                imported: prop.key.name,\n                                local: prop.value.name,\n                            });\n                        }\n\n                        // const { ...x } = require(\"p\");\n                        else if (prop.type === \"RestElement\") {\n                            if (prop.argument.type !== \"Identifier\") {\n                                throw new CompileError({\n                                    context: options.context,\n                                    span: {\n                                        start: prop.argument.start,\n                                        end: prop.argument.end,\n                                    },\n                                    message: `Unsupported require rest argument type: ${prop.argument.type}`,\n                                });\n                            }\n\n                            namespaces.push(prop.argument.name);\n                        }\n                    }\n                }\n\n                // unsupported type\n                else {\n                    throw new CompileError({\n                        context: options.context,\n                        span: {\n                            start: decl.id.start,\n                            end: decl.id.end,\n                        },\n                        message: `Unsupported variable declaration id type: ${decl.id.type}`,\n                    });\n                }\n            }\n        },\n    });\n\n    visitor.visit(result);\n\n    return {\n        isImported,\n        namespaces,\n        specifiers,\n    };\n};\n\nexport type { CollectOptions, CollectResult, Specifier };\nexport { collect };\n"],"mappings":";;;;;;AAyDA,MAAM,WAAW,YAA2C;CACxD,MAAM,SAAkB,QAAQ;CAEhC,IAAI,aAAsB;CAC1B,MAAM,aAAuB,CAAC;CAC9B,MAAM,aAA0B,CAAC;CA4IjC,IA1I6B,QAAQ;EAEjC,oBAAoB,SAAkC;GAClD,IAAI,KAAK,OAAO,UAAU,QAAQ,aAAa,OAAO,KAAK;GAE3D,aAAa;GAEb,KAAK,MAAM,aAAa,KAAK,YAEzB,IAAI,UAAU,SAAS,0BACnB,WAAW,KAAK,UAAU,MAAM,IAAI;QAInC,IAAI,UAAU,SAAS,4BACxB,WAAW,KAAK,UAAU,MAAM,IAAI;QAKnC,IAAI,UAAU,SAAS,mBACxB,IAAI,UAAU,SAAS,SAAS,cAAc;IAC1C,IACI,CAAC,QAAQ,kBAAkB,SACvB,UAAU,SAAS,IACvB,GAEA;IAEJ,WAAW,KAAK;KACZ,UAAU,UAAU,SAAS;KAC7B,OAAO,UAAU,MAAM;IAC3B,CAAC;GACL,OAII,MAAM,IAAI,aAAa;IACnB,SAAS,QAAQ;IACjB,MAAM;KACF,OAAO,UAAU,SAAS;KAC1B,KAAK,UAAU,SAAS;IAC5B;IACA,SAAS,wCAAwC,UAAU,SAAS;GACxE,CAAC;EAIjB;EAEA,sBAAsB,SAAoC;GACtD,KAAK,MAAM,QAAQ,KAAK,cAAc;IAClC,IAAI,CAAC,KAAK,MAAM;IAChB,IAAI,KAAK,KAAK,SAAS,kBAAkB;IACzC,IAAI,KAAK,KAAK,OAAO,SAAS,cAAc;IAC5C,IAAI,KAAK,KAAK,OAAO,SAAS,WAAW;IACzC,IAAI,KAAK,KAAK,UAAU,WAAW,GAAG;IAEtC,MAAM,MAA4B,KAAK,KAAK,UAAU;IAEtD,IAAI,CAAC,KAAK;IACV,IAAI,IAAI,SAAS,WAAW;IAC5B,IAAI,IAAI,UAAU,QAAQ,aAAa;IAEvC,aAAa;IAGb,IAAI,KAAK,GAAG,SAAS,cACjB,WAAW,KAAK,KAAK,GAAG,IAAI;SAI3B,IAAI,KAAK,GAAG,SAAS,iBACtB;UAAK,MAAM,QAAQ,KAAK,GAAG,YAGvB,IAAI,KAAK,SAAS,YAAY;MAC1B,IAAI,KAAK,IAAI,SAAS,cAClB,MAAM,IAAI,aAAa;OACnB,SAAS,QAAQ;OACjB,MAAM;QACF,OAAO,KAAK,IAAI;QAChB,KAAK,KAAK,IAAI;OAClB;OACA,SAAS,0CAA0C,KAAK,IAAI;MAChE,CAAC;MAGL,IAAI,KAAK,MAAM,SAAS,cACpB,MAAM,IAAI,aAAa;OACnB,SAAS,QAAQ;OACjB,MAAM;QACF,OAAO,KAAK,MAAM;QAClB,KAAK,KAAK,MAAM;OACpB;OACA,SAAS,4CAA4C,KAAK,MAAM;MACpE,CAAC;MAGL,WAAW,KAAK;OACZ,UAAU,KAAK,IAAI;OACnB,OAAO,KAAK,MAAM;MACtB,CAAC;KACL,OAGK,IAAI,KAAK,SAAS,eAAe;MAClC,IAAI,KAAK,SAAS,SAAS,cACvB,MAAM,IAAI,aAAa;OACnB,SAAS,QAAQ;OACjB,MAAM;QACF,OAAO,KAAK,SAAS;QACrB,KAAK,KAAK,SAAS;OACvB;OACA,SAAS,2CAA2C,KAAK,SAAS;MACtE,CAAC;MAGL,WAAW,KAAK,KAAK,SAAS,IAAI;KACtC;IACJ,OAKA,MAAM,IAAI,aAAa;KACnB,SAAS,QAAQ;KACjB,MAAM;MACF,OAAO,KAAK,GAAG;MACf,KAAK,KAAK,GAAG;KACjB;KACA,SAAS,6CAA6C,KAAK,GAAG;IAClE,CAAC;GAET;EACJ;CACJ,CAEM,CAAC,CAAC,MAAM,MAAM;CAEpB,OAAO;EACH;EACA;EACA;CACJ;AACJ"}