{"record":{"id":"36bacc935f5cfa27","repo":"phalcon/cphalcon","slug":"asset-path-does-not-have-a-valid-target-path","errorCode":null,"errorMessage":"Asset '{path}' does not have a valid target path","messagePattern":"Asset '(.+?)' does not have a valid target path","errorType":"exception","errorClass":"Phalcon\\Assets\\Exceptions\\InvalidAssetTargetPath","httpStatus":null,"severity":"error","filePath":"phalcon/Assets/Manager.zep","lineNumber":513,"sourceCode":"                     */\n                    if (true === empty(sourcePath)) {\n                        let sourcePath = asset->getPath();\n\n                        throw new InvalidAssetSourcePath(sourcePath);\n                    }\n                }\n\n                /**\n                 * Get the target path, we need to write the filtered content to\n                 * a file\n                 */\n                let targetPath = asset->getRealTargetPath(completeTargetPath);\n\n                /**\n                 * We need a valid final target path\n                 */\n                if (true === empty(targetPath)) {\n                    throw new InvalidAssetTargetPath(asset->getPath());\n                }\n\n                if (true === asset->isLocal()) {\n                    /**\n                     * Make sure the target path is not the same source path\n                     */\n                    if (targetPath === sourcePath) {\n                        throw new AssetSourceTargetCollision(targetPath);\n                    }\n\n                    if (true === this->phpFileExists(targetPath)) {\n                        if (filemtime(targetPath) !== filemtime(sourcePath)) {\n                            let filterNeeded = true;\n                        }\n                    } else {\n                        let filterNeeded = true;\n                    }\n                }","sourceCodeStart":495,"sourceCodeEnd":531,"githubUrl":"https://github.com/phalcon/cphalcon/blob/b7419de9cd0a8a3f48441ead84c9f8415d463e25/phalcon/Assets/Manager.zep#L495-L531","documentation":"Symmetric to the source-path check: for a filtered asset the manager computes the real target path (target base + asset targetPath); if it is empty there is nowhere to write the filtered result, and InvalidAssetTargetPath is thrown with the asset's own path in the message.","triggerScenarios":"A filtered local asset without a targetPath (and no global 'targetBasePath' option) during outputCss()/outputJs(); collections where only some assets received setTargetPath().","commonSituations":"Adding filters to an existing unfiltered asset list and forgetting output paths; relying on collection-level targetPath while filtering individual assets of a non-joined collection; missing 'targetBasePath' in Manager options.","solutions":["Set an output file per asset: `$asset->setTargetPath('js/app.min.js')`","Or set it once for the collection: `$collection->setTargetPath('js/build/')` plus a Manager 'targetBasePath'","Drop the filter if no transformation is needed, avoiding the disk write entirely"],"exampleFix":"// before\n$collection->addJs('js/app.js')->addFilter(new \\Phalcon\\Assets\\Filters\\Jsmin());\n// after\n$collection->addJs('js/app.js')\n    ->setTargetPath('js/app.min.js')\n    ->addFilter(new \\Phalcon\\Assets\\Filters\\Jsmin());","handlingStrategy":"validation","validationCode":"foreach ($collection->getAssets() as $asset) {\n    if ('' === trim((string) $asset->getTargetPath())) {\n        throw new RuntimeException('Filtered asset lacks targetPath: ' . $asset->getPath());\n    }\n}\necho $assets->outputJs($name);","typeGuard":null,"tryCatchPattern":"try {\n    echo $assets->outputJs('footer');\n} catch (\\Phalcon\\Assets\\Exceptions\\InvalidAssetTargetPath $e) {\n    $logger->error('Filtered asset has no target path: ' . $e->getMessage());\n    throw $e;\n}","preventionTips":["Set a targetPath whenever you attach a filter to an asset in a non-joined collection","Default 'targetBasePath' in the Manager options so even unset per-asset paths resolve","Lint asset definitions in CI: filter attached implies non-empty target path"],"tags":["assets","target-path","filters","configuration"],"backgroundTag":"empty-target-path","analyzedSha":"b7419de9cd0a8a3f48441ead84c9f8415d463e25","analyzedAt":"2026-08-21T06:21:18.811Z","schemaVersion":2},"datasetVersion":"2026-08-21T11:28:35.574Z"}