Skip to content

Your first scan

Goal: configure an application and its Production sources, complete a scan and inspect the corresponding dependency versions and findings.

Verified on October 10, 2026. Buttons use their actual UI labels. Application setup and scope explains sharing, roles, local decisions and scan allowances. Guide home.

Sign in to Perpensa and select the organization you want to work in. If you do not have access to an organization, follow the available onboarding flow or ask its administrator for an invitation. Accessing private data requires an authenticated session.

Adding a repository or performing a write action requires an authorized role in that organization, usually member or admin. A read-only role lets you view results but does not provide the same actions. Your plan may also limit repository additions or automation.

Choose a repository you know, with dependency files checked into version control. For example, an npm application with its package.json and package-lock.json. Importing inventory requires read access on the code hosting platform. In a monorepo, Perpensa ranks lockfiles ahead of direct manifests and can rank a deeper lockfile ahead of a root package.json. It skips node_modules, vendor, testdata, __fixtures__, and fixtures. Very large repositories publish up to 256 manifests and depth 10, with an information note if that ceiling is reached. Read failures still block publication. Public watches also keep a Partial scan after 100 useful dependency files. Large repositories and monorepos has the full rules. Supported ecosystems and files lists every file the scanner reads.

A manifest without its lock gives a declared inventory, not installed versions. A composer.json without composer.lock lists its constraints as an indicative inventory that is not checked for vulnerabilities, and its source does not count as complete coverage. In a pom.xml, versions managed by a parent POM or BOM, or set by a property not defined in that POM, are listed without a version and not checked for vulnerabilities; a scan note gives their count. Version ranges such as [1.0,2.0) are handled the same way: listed as declared, never matched. Commit the lockfile, or define an exact version in the POM, to get vulnerability matching.

If your repository contains a Dockerfile, resolved external FROM images are inventoried. After scanning, open Base images in the repository detail to inspect end-of-life and pinning checks with file/line, source links, version cycles, and security-support end dates (or an explicit unknown date). Unresolved build arguments keep their scan warning; CI may override resolved ARG defaults. These checks cover base-image support calendars, not image CVEs or OS packages. For severity, grouping and unavailable-service behavior, see Docker base images.

In Repositories → Add repository, distinguish between two uses:

Choice Use Consequence
A provider under Your repos Analyze a repository your organization can access Perpensa reads the repository; it never changes it
Track public repo, under Watch OSS Monitor a public GitHub product at a given tag or branch Tracking does not grant permission to modify the upstream project

The menu offers GitHub, Forgejo / Gitea, GitLab, and Bitbucket. Configuration depends on the provider. This walkthrough covers GitHub and public repository monitoring; a provider appearing in the menu does not guarantee that its integration is already configured.

Open GitHub. If the connection is available, select the repository from the list, then click Import selected. A repository that is already connected or inaccessible may not appear among the choices. When GitHub identity access permits it, uncovered repositories appear disabled as App not installed, with a repair action. This inventory does not grant import or scan access. A plan limit may prevent some or all of the import: read the result message before trying again.

If the screen requests authorization, follow the GitHub App installation flow. If GitHub App installation is unavailable, contact support. Import and scan require real repository access. Use Install Perpensa on another account to add a further GitHub account, even when your current installation is healthy. After installing, the application wizard resumes its saved step and draft (available for ten minutes), including after a page reload. Repair repository permissions with Authorize this repository in GitHub, then return to the window or click I’ve added the repository to refresh access.

Your organization’s verified GitHub App installation provides access to its private repositories. The App must be installed with read access to the selected repositories and linked to your organization. Signing in with GitHub alone uses identity scopes by default and does not grant private repository access. Background scans use the linked installation without your browser session. If the connection is revoked or GitHub refuses access, ask your organization’s administrator to repair that installation or its repository permissions. An installation with read access is enough to scan.

Find a repository on another connected provider

Section titled “Find a repository on another connected provider”

For Forgejo / Gitea, GitLab, or Bitbucket, open the provider and choose Import repos on the relevant connection. Search repositories filters the loaded import list immediately by owner or repository name, without regard to letter case. Leading and trailing spaces are ignored. Clear the field to see all importable repositories again; already connected repositories remain excluded.

No repositories match your search. means the filter has no matches, not that the connection has no repositories. The search only covers repositories returned by that connection; it does not request additional results from the provider or change your access permissions.

Selected repositories remain selected even when the filter hides them. The count on Import selected includes all selections, visible or hidden; clear the search to review them before importing. Opening an import list, switching connections, or reopening the dialog clears the search.

Open Track public repo, enter the public GitHub repository, then choose an available reference to track. A tag identifies a named version; a branch may change between scans. Check the reference type and value before confirming.

In the fictional example example/server, tracking v1.2.0 means analyzing that product reference. It changes neither your installation of the server nor the upstream repository. The tracked repository shows a Public watch badge. Signing in does not change a public watch’s access. If GitHub limits requests, Waiting for GitHub shows when an automatic retry is expected. The same scan stays queued; you do not need to start another one. The estimated retry time may move if GitHub is still limiting requests.

3. Create Production and wait for its source results

Section titled “3. Create Production and wait for its source results”

In Applications, select Create application. Define the name and Production declarations, associate catalog repositories with exact branches/tags, then review and create. Connection and repository import do not themselves start a scan. New sources receive one initial scan after creation; an already followed source is reused without another initial scan. Creation is available on Starter too.

Open the application to check its source states and dated results. Scan source requests a refresh from an environment. Repository details preserve historical scans and provide the application/source links; they do not offer autonomous repository scans. A queued or running scan is not a completed result.

Incomplete coverage cannot replace the last complete score. A source error can reuse a complete result for three days from the first failure, clearly dated and signalled. After expiry, the score is unavailable. Use Reconnect or Remove next to an affected source with an authorized role. A moved tag requires an audited preview/confirmation covering all affected environments before its new content is read. Source states and grace.

Where to look What to check What this does not prove
Inventory or inventory on the repository details page Observed dependency names, versions, and files That every file and ecosystem in the repository is covered
Findings Matches with vulnerability advisories That every vulnerability is exploitable in your deployment
Update queue Ranked candidate updates That every finding has a known fixed version

Find a dependency whose version you know in Inventory. Then open a finding for that repository, if there is one, and inspect its observed version, indicators, and Open update when an update exists. One update can address several findings, so the numbers of findings and updates are not necessarily equal. Copy prompt on a Findings row hands the fix to your coding agent; see Remediate a vulnerability.

Overview aggregates the deduplicated union of Production application sources. For this first check, focus on the repository and version you just analyzed: an overall total may include other repositories or older results.

Perpensa recognizes *.rockspec and luarocks.lock, including in subprojects. It reads literal Lua data without executing Lua or installing packages. Strings, comments, literal tables and bracketed literal keys are supported. Simple local version variables and metadata expressions are skipped without evaluation, including comparisons and metadata-only if branches. Dependency tables must be literal; function calls, conditional dependencies, other control flow and dependency mutations are unsupported; unsupported or invalid files receive a diagnostic. Files are limited to 1 MiB and tables to 32 levels, in addition to the repository discovery limits.

Inventory keeps each declared constraint separate from the resolved lock version. Without a matching lock entry in the same directory, Version unresolved is shown, including for an exact == declaration. A locked version preserves the rock revision (for example 3.1.0-1); it does not verify an actual installation. The component detail shows the originating files, constraints and categories. Multiple rockspecs retain their origins; differing declarations are diagnosed without choosing one or checking compatibility.

Runtime dependencies are production packages; build and test dependencies are development packages. lua is reported as a runtime requirement, not an installed rock. Native external_dependencies are excluded. Platform-dependent dependency tables are diagnosed as incomplete; no platform is chosen automatically. A lock without a rockspec has unknown directness.

Vulnerability coverage is unavailable for LuaRocks. This delivery provides inventory only: no LuaRocks CVE matching or constraint resolution. No findings does not establish safety. The posture score is unavailable when its scope includes LuaRocks; findings for other ecosystems remain available. SBOM exports preserve the declared constraints and omit the version when unresolved. The machine API exposes optional luarocks metadata and vulnerability_coverage on these packages. A CI check with LuaRocks coverage returns an indeterminate security result.

Situation Next check
Add repository is missing or an action is denied Active organization, role, and plan limits
Repository missing from import Connection to the correct account, read permissions, repository already added
Scan remains queued Job status; contact support if the wait persists
Scan failed Error message, access to the code hosting platform, reference still exists
Empty inventory Files present at the scanned reference and support for their format
Inventory present, no findings Vulnerability sources, scan coverage, and active filters
Finding present, no update Unknown fixed version (No fix yet) or no applicable target

You have completed this walkthrough when the scan is finished and you can identify what it actually inventoried, even if it found no vulnerabilities. Continue with Understand the results, then Remediate a vulnerability.