Updated June 13, 2015 with additional guidance for Lightning Components


Assumptions:

  • This article assumes that you are a Developer / Security Professional who understands security best practices.
  • Please see the OWASP Secure Coding Practices - Quick Reference Guide for a basic overview of application security concepts.
  • Partners are required to follow secure best practices as well as the guidelines described on this page.
  • Specific requirements for a each application will vary depending on platform architecture etc.
  • The review is a slightly subjective process whereby the organization size, application architecture, data handling, etc. are taken into consideration.


Force.com Code

All Force.com code on the AppExchange must be in managed packages. Once a package version is submitted for security review only that package version will be reviewed. If there are updates since submitting for security review file a case on the partner portal.

Apex:

  • Sharing: Use the “with sharing” keyword when declaring a class to respect sharing rules that apply to current users, unless there is a specific and valid business case to over-ride this which should be marked in false positive document
    • Controllers retrieving user-specified objects as well as global classes must always use sharing.
    • Classes that modify standard fields must use sharing.
    • Classes that modify only custom fields owned by the partner and that are not entry points to the app may use without sharing if they prefer to enforce their own security controls rather than those of the platform.
  • CRUD and FLS: Enforce and respect FLS (Field Level Security) and CRUD (Create, Read, Update, Delete) settings configured by your customer's org administrator when accessing fields that you do not own (standard fields). More information can be found on the Force.com Secure Cloud Development site under Testing CRUD and FLS Enforcement and in the developerforce CRUD/FLS guide .
  • Shield: Enforce the encryption model put in by shield by using Schema.sObjectType.Contact.fields.Phone.isEncrypted() and checking whether or not the user has the permission PermissionsViewEncryptedData. For more info see Enforcing Encryption
  • Cross-Site Request Forgery in Visualforce pages: Avoid doing DML operations in page actions or in any action that runs automatically (e.g. javascript submitting forms on page load) Secure Coding Cross Site Request Forgery If it is required within a Visualforce page, select the Require CSRF Protection on GET requests option, as described by Visualforce help documentation
  • Triggers: Ensure triggers are bulkified.
  • Metadata: If your package accesses metadata during installation or update, or contains a custom setup interface that accesses metadata, you must notify the user. The notice should let customers know that your package has the ability to modify the subscriber org’s metadata. For installs that access metadata, notify the user in the description of your package.
  • Tests: Use System.assert methods as much as possible to prove that code behaves properly. This is key to ensure that the Apex code executes to the expected value or behavior. More information on Best Practices can be found here: http://wiki.developerforce.com/index.php/An_Introduction_to_Apex_Code_Test_Methods


VisualForce

  • In visualforce mergefields, properly escape all string types based on the rendering context: In html text nodes, no escaping is necessary. Within script tags or javascript event handlers, mergefields should be wrapped with JSENCODE() and then quoted. Do not place mergefields that are of string type within style tags.
  • Do not place visualforce mergefields within client side micro templates (for example, angular templates). Rather, you can assign the quoted mergefield to a javascript variable within a script tag and then pass the variable to the compiled template or to the client side controller.

Custom Javascript & HTML:

  • In order to prevent XSS attacks, your application must properly output encode data for the appropriate rendering operations (e.g. element.innerHTML=…, a.href=...).
  • JavaScript that is part of partner offerings should not execute within the context of the Salesforce.com application. Partner JavaScript may only execute within the context of Visualforce. This means that any OnClickJavascript in custom buttons or weblinks is grounds for failure.
  • All script and style resources must be loaded via static resources. Do not load resources dynamically with a link or script tag. Do not hotlink to javascript code outside of static resources.
  • To aid in reviewing custom javascript, include un-minified source files when submitting for the security review corresponding to all minified files in static resources. Please give the unminified files the same name (except .min), for scanning purposes. Do not combine unminified and minified files together. Also include source files for all languages that transpile to javascript in your code (e.g. JSX). Auxiliary source files should be provided in static resources.

Storing Sensitive Information (e.g. credentials or API keys to other applications):

  • Ensure that sensitive information is not available to all users in a customer org. This can be achieved by using Custom Settings or Custom Metadata Types in “Protected” mode and creating a Visualforce page for authorized users to update information. The previously stored data should not be displayed back to the user on this page (define a null getter and also mark the variable as private and transient). Another option is to implement Apex Crypto and store the encryption key in a protected custom setting. For more information see the Secure Cloud Development entry for Storing Secrets.


For detailed information and guidance on the issues above, please refer to Apex & VisualForce Security Tips

Client (Desktop) and Composite (Hosted) Applications

Make sure you provide us access to a remote testing environment where we can test your client app.

Policies

  • Implement an Information Security Policy that is periodically reviewed, approved by Senior Management, and communicated to all employees.


Standards & Procedures

  • System Configuration
  • Application Development
  • Application Configuration
  • Database Configuration
  • Network Configuration (Including Firewall/IDS)
  • Patching Process
  • Logging Process/Log Review
  • Physical Security
  • Incident Management Process
  • Authentication & Authorization
  • Encryption Standard


Host/Platform Security

  • Disable unnecessary services on key servers (web application, database, etc.)
  • Run up-to-date versions of all services on key servers.
  • Implement robust patch management
  • Remove/Rename default accounts and change default passwords
  • Securely hash all passwords with a unique, random salt
  • Create unique usernames for all users
  • Implement a robust password policy (organizational and application)
    • Minimum 8 characters
    • Combination (2 out of 4) of numbers, letters (lower and upper) and special characters
    • Enable lock outs for bad attempts (3-5)
    • Enable password expiration (90-180 days)
    • Enable password history (don’t allow reuse of last 3 passwords)
    • Passwords should not be sent to third parties (Google analytics, fullstory)
  • Implement system logging and enforce periodic review of logs
  • Implement host based firewalls on critical systems
  • Implement secure remote access (VPN – SSHv2, SSL, IPSEC, or AES)
    • Persistent tunnels configured with appropriate ACLs
  • Implement an enterprise-wide anti-virus solution with daily updates
  • Remote Desktop or Terminal Services Remote Administration should not be exposed to Internet facing connections.

Application Security

  • Reverse Proxy based apps are not allowed on the AppExchange.
  • Implement a strong SDLC with security being a core component
    • Implement code reviews
    • Implement a testing/QA methodology
    • Implement a methodology for rolling code to production
  • Implement appropriate segregation of duties within the test, development and production environments
  • Unless necessary, do not store salesforce.com credentials (leverage the Session IDs)
    • If necessary, have a clear rationale and communicate this to salesforce.com
  • Implement encryption in transmission and storage (login credentials and salesforce.com customer data)
    • Support TLSv1.1 and newer versions
      • TLS 1.0 is only supported until July 22, 2017.
      • Strong configurations are also required. See https://www.ssllabs.com/ssltest/ for a security rating for your configuration
    • Set "secure" flag on session cookies
    • Do not store encryption keys in source code
    • Implement encryption key management
  • Prevent username enumeration
    • Do not give different feedback to the user if the account does or does not exist in password reset pages
  • Use CAPTCHA's or other defenses against automated login attempts
  • Do not allow login CSRF (forced login)
  • Avoid Dynamic SQL
    • If Using Dynamic SQL, prepare appropriate rationale for salesforce.com
    • Implement appropriate compensating controls
  • Implement appropriate input validation and URL cleansing to prevent SQL Injection and Cross-Site Scripting (XSS) attacks
  • All script and style resources must be loaded via static resources. Do not load resources with a link or script tag. Do not hotlink to js code outside of static resources.
  • Implement controls to protect the Salesforce Session ID. Specifically:
    • Session ID should always be encrypted in transmission
    • Session ID should not be sent to third parties (Example: Google Analytics)
    • Validate that the connection is being requested from a valid Salesforce server. Below is the regex to validate legitimate SFDC SOAP servers:
^https://[^/?]+\\.(sales|visual\\.)force\\.com/services/(S|s)(O|o)(A|a)(P|p)/(u|c)/.*


Operational Security

  • Actively monitor your network
  • Implement and periodically test Disaster Recovery and Business Continuity Plans
  • Implement an Employee Training and Security Awareness Program
  • Implement Encryption Key and Privileged User Password Rotation
  • Implement a robust change management process which includes documentation and approval of all changes
  • Perform security review of third-party organizations


Network Security (Hosted Applications Only)

  • Stateful Packet Inspection Firewall
  • Segregation of Web/Application and database servers
  • Network IDS/IPS implemented (required if critical Salesforce data is stored in external servers)
  • Log aggregation, alerting and daily review for key network devices, application and database servers
  • Wireless Networking
    • No wireless in collocation facilities
    • WPA2 and wireless IDS implemented at corporate
  • E-mail Spam filter


Physical Security (Hosted Applications Only)

  • Restrict data center access to authorized personnel
  • Maintain physical access logs at the data center
  • Implement security cameras, motion detectors and alarms at data centers that are monitored on a 24/7/365 basis
  • Implement controls to to prevent the infrastructure against external threats and hazards (fire, earthquake, flooding, etc.)


Trial Templates

  • Organization default security settings must not be changed. (Password policy, timeout, SSL settings, etc.)
  • Packages included in trials must be approved on the AppExchange.
  • No unpackaged code or other components may be distributed in trials.


Lightning Components

Familiarize yourself with the framework's lifecycle and follow the best practices in the Lightning Component Developer's Guide:

  • Review requirements
    • If submitting a stand alone component, please include an app container in the DE org so that the component is usable. If the intended app container is the Salesforce1 app, please document this and be sure to create the appropriate tabs so that the component is visible in One.app. Please make it clear how to access and use the app/component after logging into the test org.
    • Locker Compliance will be mandatory to submit for the security review. Therefore, the Developer Edition test environment provided for the security review must have Locker Service enabled and the security review will be performed with Locker Service enabled.
    • All Lightning Components are required to be running on API v40 or above. More details here.
    • To aid in reviewing components, include un-minified source files when submitting the component for the security review corresponding to all minified files in static resources. Please give the unminified files the same name (except .min), for scanning purposes. Do not combine unminified and minified files together. Also include source files for all languages that transpile to javascript in your code (e.g. JSX). Auxiliary source files should be provided in static resources.
  • App structure
    • When global component attributes or app events flow into possible HTML rendering contexts, it must be documented in the documentation for the component, or the description attribute of tha aura:attribute. This is to inform other developers that you these attributes may be dangerous.
    • Lightning components or apps should not include or generate <script> tags. Lightning components should not generate <style> tags.
    • Avoid in line javascript with the exception of event handlers that call controller methods. They cannot call methods of the helper or of a loaded script resource.
    • Methods in helpers or script resources must (ultimately) be called from a renderer or controller of the same component.
      • All script and style resources must be loaded with an ltng:require component and must be stored in static resources. Do not load resources with a link or script tag. Do not hotlink to js code outside of static resources.
      • Do not use deprecated functions such as newComponent(). Use the latest functions for the framework at the time of submission.
    • Do not override browser window or document built-in methods.
    • Avoid unsafe javascript constructs, such as eval() or Function.prototype.constructor(). Code should be written to work with a CSP policy that bans eval as well as unsafe-inline, even if the component may be surfaced in an environment that does not serve these directives.
    • Lightning components must not overlay and allow clickthrough to components from other namespaces.
    • If submitting Lightning Container Components to the Appexchange, you must include unminified and untranspiled sources as a part of your review. Reviews without readable code will be sent back.
  • Lightning Authorization
    • Make sure apex controllers and other entry points to the app run 'with sharing'. Do not omit the sharing keyword from any class that accesses data.
    • Perform CRUD/FLS checks when returning data to the client or when querying fields in a SOQL query as the platform does not do this for you.
  • Respect the Aura rendering lifecycle
    • Renderers should not fire events and should not modify component attributes that belong to another component.
    • When re-entering the framework from outside the framework's lifecycle (for example asynchronous javascript such as setTimeout), obtain a reference to an action via $A.getCallback() so that your code can properly run in the context of your component.
    • When doing animations, CSS animations are recommended. For Javascript animations, please check that the DOM element exists so that your code does not throw exceptions should your component be unrendered while the animation is occurring.
    • Components should not read or modify DOM elements not belonging to the component.
  • Security and code correctness
    • Sensitive attribute values in expression language: assignments to URLs are sensitive because they can contain javascript pseudo-schemes or lead to URL redirection attacks. Sanitize all assignments to hrefs, svg xlinkhrefs, and other URLs to ensure that they do not contain "javascript:". iframe srcdoc and iframe src are also sensitive and must be treated similarly. For a full list of sensitive attribute values see html5 security cheatsheet
    • Do not assign user data to window.location without first verifying it does not contain a 'javascript:' pseudo scheme and has the correct host. If you are using third party libraries, please audit them to determine which sensitive sinks are present and sanitize/encode data before passing it to those sinks.
    • Treat all public and global component attributes as untrusted (e.g. under the controller of an attacker), and sanitize values prior to using them in a renderer or other dangerous context such as an unescapedHTML. If they must be passed into these contexts unescape, clearly state that in your components documentation
    • In a renderer, avoid use of innerHTML and other html rendering functions when possible. We currently do not provide escaping libraries to make these functions safe.
    • Be aware of CSRF issues and do not initiate server-side DML operations in an event handler fired automatically by the platform, such as init, or afterRender. Server-side DML operations may only be initiated by user interaction events, such as press.