Yelp/detect-secrets

How to show the raw plain text secret detected by detect-secrets?

setu1421 opened this issue · 3 comments

I want to retrieve the exact matched string from hashed secret provided by the tool. So, I ran the detect-secrets tool for willymcallister/spinningnumbers repository and a sample output of the tool is shown below:

image

The tool has found a private key in line 184 of _articles/staticman-heroku.md file.

image

However, I tried to compute the hashed secret using hashlib with different combinations of the secrets such as by removing unnecessary texts. But I could not compute the exact hashed secret provided by the tool.

image

Which part of the actual secret string has been used to calculate the hashed secret? Or Is there any way to get the plain text secret instead of hashed secret in the report using any flag? Please let me know your feedback.

Hey, you can go into the library and remove a line in detect_secrets/core
/potential_secret.py at line number 56 , and insert this: self.secret_hash: str = secret

Better yet, you can keep the secret_hash field and instead just add this to the json() function that starts on line 98 of detect_secrets/core/potential_secret.py:

attributes['raw_secret'] = self.secret_value

So the modified function would look like this:

    def json(self) -> Dict[str, Union[str, int, bool]]:
        """Custom JSON encoder"""
        attributes: Dict[str, Union[str, int, bool]] = {
            'type': self.type,
            'filename': self.filename,
            'hashed_secret': self.secret_hash,
            'is_verified': self.is_verified,
        }

        if hasattr(self, 'line_number') and self.line_number:
            attributes['line_number'] = self.line_number

        if hasattr(self, 'is_secret') and self.is_secret is not None:
            attributes['is_secret'] = self.is_secret

        # Include plaintext secret (NOT RECOMMENDED DUE TO SECURITY CONCERNS)
        attributes['raw_secret'] = self.secret_value

        return attributes

For one project, I personally modified it to also include the full line of source code that contains the secret (for easier contextual understanding):

    def json(self) -> Dict[str, Union[str, int, bool]]:
        """Custom JSON encoder"""
        attributes: Dict[str, Union[str, int, bool]] = {
            'type': self.type,
            'filename': self.filename,
            'hashed_secret': self.secret_hash,
            'is_verified': self.is_verified,
        }

        if hasattr(self, 'line_number') and self.line_number:
            attributes['line_number'] = self.line_number
            
            # Include the relevant line of source code (NOT RECOMMENDED DUE TO SECURITY CONCERNS)
            with open(os.path.abspath(self.filename)) as fp:
                for i, line in enumerate(fp):
                    if i == self.line_number-1:
                        attributes['source_code'] = line.strip()
                        break

        if hasattr(self, 'is_secret') and self.is_secret is not None:
            attributes['is_secret'] = self.is_secret

        # Include plaintext secret (NOT RECOMMENDED DUE TO SECURITY CONCERNS)
        attributes['raw_secret'] = self.secret_value

        return attributes

Your resulting findings will look like this:

// ...
{
  "type": "GitHub Token",
  "filename": "src/test.js",
  "hashed_secret": "ffffffffffffffffffffffffffffffffffffffff",
  "is_verified": false,
  "line_number": 451,
  "raw_secret": "ghp",
  "source_code": "let ghToken = \"ghp_AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA\";"
},
// ...

Note, of course, that none of this is recommended - it's bad practice to unnecessarily store plain-text secrets.

Hello everyone, @SeanPesce is right in bringing up the fact that writing the raw secrets in .secrets.baseline is a security issue and defeats the purpose of running detect-secrets to avoid pushing those secrets to your remote repository. I'll change the status of this issue as won't fix for now, but won't close it so it can stay under our radar and we (and you all) can find a solution to address this in a way that would make sense.