Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[PM-14476] Avoid multiple lookups in dictionaries #4973

Open
wants to merge 8 commits into
base: main
Choose a base branch
from

Conversation

Henr1k80
Copy link

@Henr1k80 Henr1k80 commented Nov 4, 2024

🎟️ Tracking

I looked at the code and saw there was a lot of unneeded dictionary lookups.
I want to remove these to avoid spending CPU time on generating hash values for lookups.

📔 Objective

Improve performance + scalability plus reduce carbon impact.

I know that I have touched a lot of files, but I was easier to just do it everywhere, than to find the hot paths and only fix it there.
A benefit is that the code is more correct everywhere. ⛏

⏰ Reminders before review

  • Contributor guidelines followed
  • All formatters and local linters executed and passed
  • Written new unit and / or integration tests where applicable
  • Protected functional changes with optionality (feature flags)
  • Used internationalization (i18n) for all UI strings
  • CI builds passed
  • Communicated to DevOps any deployment requirements
  • Updated any necessary documentation (Confluence, contributing docs) or informed the documentation team

🦮 Reviewer guidelines

  • 👍 (:+1:) or similar for great changes
  • 📝 (:memo:) or ℹ️ (:information_source:) for notes or general info
  • ❓ (:question:) for questions
  • 🤔 (:thinking:) or 💭 (:thought_balloon:) for more open inquiry that's not quite a confirmed issue and could potentially benefit from discussion
  • 🎨 (:art:) for suggestions / improvements
  • ❌ (:x:) or ⚠️ (:warning:) for more significant problems or concerns needing attention
  • 🌱 (:seedling:) or ♻️ (:recycle:) for future improvements or indications of technical debt
  • ⛏ (:pick:) for minor or nitpick changes

@Henr1k80
Copy link
Author

Henr1k80 commented Nov 4, 2024

Oh, and there are a few places where I avoid allocating a new empty array or list

@bitwarden-bot
Copy link

Thank you for your contribution! We've added this to our internal Community PR board for review.
ID: PM-14476
Link: https://bitwarden.atlassian.net/browse/PM-14476

@bitwarden-bot bitwarden-bot changed the title Avoid multiple lookups in dictionaries [PM-14476] Avoid multiple lookups in dictionaries Nov 4, 2024
jonashendrickx
jonashendrickx previously approved these changes Nov 5, 2024
Copy link
Contributor

@jrmccannon jrmccannon left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thank you again for your contribution. Everything looks good. Just had a couple requests for consistency and a few to improve clarity.

src/Api/Vault/Models/Response/CipherResponseModel.cs Outdated Show resolved Hide resolved
src/Api/Vault/Models/Response/CipherResponseModel.cs Outdated Show resolved Hide resolved
Comment on lines +252 to 258
if (providers == null || !providers.TryGetValue(provider, out var twoFactorProvider))
{
return false;
}

return providers[provider].Enabled && Use2fa;
return twoFactorProvider.Enabled && Use2fa;
}
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🎨 This could be inverted for clarity. Something like this might be better.

    public bool TwoFactorProviderIsEnabled(TwoFactorProviderType provider)
    {
        var providers = GetTwoFactorProviders();

        if (providers?.TryGetValue(provider, out var value) ?? false)
        {
            return value.Enabled && Use2fa;
        }

        return false;
    }

Copy link
Author

@Henr1k80 Henr1k80 Nov 7, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I went for minimum changes in lines of code, to avoid reviewing logical changes as well.

And I believe that guard clauses should be in top, to be consistent with the rest of the code.
It is also my personal preference

src/Core/AdminConsole/Entities/Organization.cs Outdated Show resolved Hide resolved
Comment on lines +943 to +948
if (providers is null || !providers.TryGetValue(type, out var provider))
{
return;
}

providers[type].Enabled = true;
provider.Enabled = true;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🎨 Inverting this might help with clarity

Something like this maybe:

        var providers = organization.GetTwoFactorProviders();
        if (providers?.TryGetValue(type, out var twoFactorProvider) ?? false)
        {
            twoFactorProvider.Enabled = true;
            organization.SetTwoFactorProviders(providers);
            await UpdateAsync(organization);
        }

src/Core/Entities/User.cs Outdated Show resolved Hide resolved
{
_attachmentContainers[containerName] = _blobServiceClient.GetBlobContainerClient(containerName);
attachmentContainer = _blobServiceClient.GetBlobContainerClient(containerName);
_attachmentContainers[containerName] = attachmentContainer;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🎨 The container shouldn't be added to the dictionary until it is successfully created.

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

In the existing code, it is already added before the creation.

If you are worried about concurrency issues, the _attachmentContainers Dictionary should also be changed to be a ConcurrentDictionary to avoid concurrency issues

If concurrency should be supported, I suggest doing it in a separate pull request

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants