def index():

    # Get an instance of the Authentication class.
    auth = Authentication()

    # Set PKI default options (see utils.py).
    set_pki_defaults(auth)

    # Start the authentication. Receive as response a AuthStartResult instance
    # containing the following fields:
    # - nonce: The nonce to be signed. This value is also used on "complete"
    #          action.
    # - digest_algorithm: The digest algorithm that will inform the Web PKI
    #                     component to compute the signature.
    result = auth.start()

    # Render the fields received form start() method as hidden field to be used
    # on the javascript and on the "complete" step. We pass the nonce as base64
    # to be rendered on page.
    response = make_response(
        render_template('authentication_express/index.html',
                        nonce=result.nonce,
                        digest_algorithm=result.digest_algorithm))

    # The nonce acquired above can only be used for a single authentication
    # attempt. In order to retry the signature it is necessary to get a new
    # token. This can be a problem if the user uses the back button of the
    # browser, since the browser might show a cached page that we rendered
    # previously, with a now stale token. To prevent this from happening, we
    # call the method set_no_cache_headers(), which sets HTTP headers to prevent
    # caching of the page.
    get_expired_page_headers(response.headers)

    return response
def index(file_id):

    # Verify if the provided "file_id" exists.
    file_path = join(current_app.config['APPDATA_FOLDER'], file_id)
    if not exists(file_path):
        return render_template('error.html', msg='File not found')

    # Get an instance of the PadesSigner class, responsible for receiving
    # the signature elements and performing the local signature.
    signer = PadesSigner()

    # Set PKI default options (see utils.py).
    set_pki_defaults(signer)

    # Set signature policy.
    signer.signature_policy = standard_signature_policies.PADES_BASIC_WITH_LTV

    # Set PDF to be signed.
    signer.set_pdf_to_sign_from_path(file_path)

    # The PKCS #12 certificate path.
    signer.set_pkcs12_from_path(
        join(current_app.static_folder, 'Pierre de Fermat.pfx'))
    # Set the certificate's PIN.
    signer.cert_password = '******'

    # Set a file reference for the stamp file. Note that this file can be
    # referenced later by "fref://{alias}" at the "url" field on the visual
    # representation (see content/vr.json or get_visual_representation()
    # method).
    signer.add_file_reference('stamp', get_pdf_stamp_path())

    # Set visual representation. We provide a dictionary that represents the
    # visual representation JSON model.
    signer.set_visual_representation(
        PadesVisualElementsExpress.get_visual_representation())

    # Generate path for output file and add to signer object.
    create_app_data()  # Guarantees that "app data" folder exists.
    output_file = '%s.pdf' % (str(uuid.uuid4()))
    signer.output_file = join(current_app.config['APPDATA_FOLDER'],
                              output_file)

    # Perform the signature.
    signer_cert = signer.sign(get_cert=True)

    response = make_response(
        render_template('pades_server_key_express/index.html',
                        signer_cert=signer_cert,
                        signed_pdf=output_file))
    get_expired_page_headers(response.headers)

    return response
Example #3
0
def index(file_id=None):
    # Verify if the provided "file_id" exists.
    file_path = join(current_app.config['APPDATA_FOLDER'], file_id)
    if not exists(file_path):
        return render_template('error.html', msg='File not found')

    # Get an instance of the CadesSigner class, responsible for receiving
    # the signature elements and performing the local signature.
    signer = CadesSigner()

    # Set PKI default options (see utils.py).
    set_pki_defaults(signer)

    # Set signature policy.
    signer.signature_policy = \
        standard_signature_policies.PKI_BRAZIL_CADES_ADR_BASICA

    # Set file to be signed. If the file is a CSM, the PKI Express will
    # recognize that and will co-sign that file.
    signer.set_file_to_sign_from_path(file_path)

    # The PKCS #12 certificate path.
    signer.set_pkcs12_from_path(
        join(current_app.static_folder, 'Pierre de Fermat.pfx'))
    # Set the certificate's PIN.
    signer.cert_password = '******'

    # Set 'encapsulate content' option (default: True).
    signer.encapsulated_content = True

    # Generate path for output file and add to signer object.
    create_app_data()  # Guarantees that "app_data" folder exists.
    output_file = '%s.p7s' % (str(uuid.uuid4()))
    signer.output_file = join(current_app.config['APPDATA_FOLDER'],
                              output_file)

    # Perform the signature.
    signer_cert = signer.sign(get_cert=True)

    response = make_response(
        render_template('cades_server_key_express/index.html',
                        signer_cert=signer_cert,
                        cms_file=output_file))
    get_expired_page_headers(response.headers)

    return response
Example #4
0
def full():
    """

    This function initiates a XML element signature using REST PKI and renders
    the signature page. The full XML signature is recommended in cases which
    there is a need to sign the whole XML file.

    """

    try:

        # Get an instance of the FullXmlSignatureStarter class, responsible for
        # receiving the signature elements and start the signature process.
        signature_starter = FullXmlSignatureStarter(get_restpki_client())

        # Set the XML to be signed, a sample XML Document.
        signature_starter.set_xml_to_sign(get_sample_xml_document_path())

        # Set the location on which to insert the signature node. If the
        # location is not specified, the signature will appended to the root
        # element (which is most usual with enveloped signatures).
        nsm = NamespaceManager()
        nsm.add_namespace('ls', 'http://www.lacunasoftware.com/sample')
        signature_starter.set_signature_element_location(
            '//ls:signaturePlaceholder', XmlInsertionOptions.APPEND_CHILD, nsm)

        # Set the signature policy.
        signature_starter.signature_policy = \
            StandardSignaturePolicies.XADES_BES

        # Set the security context to be used to determine trust in the
        # certificate chain. We have encapsulated the security context choice on
        # util.py.
        signature_starter.security_context = get_security_context_id()

        # Call the start_with_webpki() method, which initiates the signature.
        # This yields the token, a 43-character case-sensitive URL-safe string,
        # which identifies this signature process. We'll use this value to call
        # the signWithRestPki() method on the Web PKI component (see
        # signature-form.js javascript) and also to complete the signature after
        # the form is submitted (see method pades_signature_action()). This
        # should not be mistaken with the API access token.
        result = signature_starter.start_with_webpki()

        # The token acquired above can only be used for a single signature
        # attempt. In order to retry the signature it is necessary to get a new
        # token. This can be a problem if the user uses the back button of the
        # browser, since the browser might show a cached page that we rendered
        # previously, with a now stale token. To prevent this from happen, we
        # force page expiration through HTTP headers to prevent caching of the
        # page.
        response = make_response(
            render_template('xml_signature/full.html', token=result.token))
        response.headers = get_expired_page_headers()
        return response

    except Exception as e:
        return render_template('error.html', msg=e)
Example #5
0
def index():
    # Instantiate the XmlElementSignatureStarter class, responsible for
    # receiving the signature elements and start the signature process.
    signature_starter = XmlElementSignatureStarter(get_rest_pki_client())

    # Set the XML to be signed, a sample XML Document.
    signature_starter.set_xml_to_sign(get_sample_nfe_path())

    # Set the ID of the element to be signed.
    signature_starter.to_sign_element_id = \
        'NFe35141214314050000662550010001084271182362300'

    # Set the signature policy.
    signature_starter.signature_policy = \
        StandardSignaturePolicies.NFE_PADRAO_NACIONAL

    # Set a security context to be used to determine trust in the
    # certificate chain. We have encapsulated the security context choice on
    # util.py.
    signature_starter.security_context = get_security_context_id()

    # Call the start_with_webpki() method, which initiates the signature.
    # This yields the token, a 43-character case-sensitive URL-safe string,
    # which identifies this signature process. We'll use this value to call
    # the signWithRestPki() method on the Web PKI component (see
    # signature-form.js javascript) and also to complete the signature after
    # the form is submitted (see method action()). This should not be
    # mistaken with the API access token.
    result = signature_starter.start_with_webpki()

    # The token acquired above can only be used for a single signature
    # attempt. In order to retry the signature it is necessary to get a new
    # token. This can be a problem if the user uses the back button of the
    # browser, since the browser might show a cached page that we rendered
    # previously, with a now stale token. We force page expiration through
    # HTTP headers to prevent caching of the page.
    response = make_response(
        render_template('xml_nfe_signature_rest/index.html',
                        token=result.token))
    get_expired_page_headers(response.headers)
    return response
def index():
    """

    This view function initiates an authentication with REST PKI and renders
    the authentication page.

    """

    try:

        # Get an instance of the Authentication class.
        auth = get_rest_pki_client().get_authentication()

        # Call the start_with_web_pki() method, which initiates the
        # authentication. This yields the "token", a 22-character case-sensitive
        # URL-safe string, which represents this authentication process. We'll
        # use this value to call the signWithRestPki() method on the Web PKI
        # component (see signature-form.js) and also to call the
        # complete_with_web_pki() method on the route /authentication/action.
        # This should not be mistaken with the API access token. We have
        # encapsulated the security context choice on util.py.
        token = auth.start_with_web_pki(get_security_context_id())

        # The token acquired above can only be used for a single
        # authentication. In order to retry authenticating it is necessary to
        # get a new token. This can be a problem if the user uses the back
        # button of the browser, since the browser might show a cached page that
        # we rendered previously, with a now stale token. To prevent this from
        # happening, we force page expiration through HTTP headers to prevent
        # caching of the page.
        response = make_response(
            render_template('authentication_rest/index.html', token=token))
        get_expired_page_headers(response.headers)
        return response

    except Exception as e:
        return render_template('error.html', msg=e)
Example #7
0
def index(file_to_sign=None, file_to_cosign=None):
    """

    This function initiates a CAdES signature using REST PKI and renders the
    signature page.

    All CAdES signature examples converge to this action, but with different
    URL arguments:

        1. Signature with a server file               : no arguments filled
        2. Signature with a file uploaded by the user : "******" filled
        3. Co-signature of a previously signed CMS    : "cmsfile" filled

    """

    try:

        # Get an instantiate of the CadesSignatureStarter class, responsible for
        # receiving the signature elements and start the signature process.
        signature_starter = CadesSignatureStarter(get_restpki_client())

        if file_to_cosign is not None:
            # If the URL argument "cmsfile" is filled, the user has asked to
            # co-sign a previously signed CMS. We'll set the path to the CMS to
            # be co-signed, which was previously saved in the "app-data" folder
            # by the action() step. Note two important things:
            #
            #   1. The CMS to be co-signed must be set using the method
            #      "set_cms_to_cosign", not the method "set_file_to_sign".
            #
            #   2. Since we're creating CMSs with encapsulated content (see call
            #      to encapsulated_content property below), we don't need to set
            #      the content to be signed, REST PKI will get the content from
            #      the CMS being co-signed.
            #
            signature_starter.set_cms_to_cosign_path(
                '%s/%s' %
                (current_app.config['APPDATA_FOLDER'], file_to_cosign))
        else:
            # If the URL argument "userfile" is filled, it means the user was
            # redirected here by "upload" view (signature with file uploaded by
            # user). We'll set the path of the file to be signed, which was
            # saved in the app_data folder by "upload" view.
            signature_starter.set_file_to_sign_path(
                '%s/%s' % (current_app.config['APPDATA_FOLDER'], file_to_sign))

        # Set the signature policy.
        signature_starter.signature_policy =\
            StandardSignaturePolicies.PKI_BRAZIL_CADES_ADR_BASICA

        # Set a security context to be used to determine trust in the
        # certificate chain. We have encapsulated the security context choice on
        # util.py.
        signature_starter.security_context = get_security_context_id()

        # Optionally, set whether the content should be encapsulated in the
        # resulting CMS. If this parameter is ommitted, the following rules
        # apply:
        #
        # - If no CmsToCoSign is given, the resulting CMS will include the
        # content.
        # - If a CmsToCoSign is given, the resulting CMS will include the
        # content if and only if the CmsToCoSign also includes the content.
        #
        signature_starter.encapsulate_content = True

        # Call the start_with_webpki() method, which initiates the signature.
        # This yields the token, a 43-character case-sensitive URL-safe string,
        # which identifies this signature process. We'll use this value to call
        # the signWithRestPki() method on the Web PKI component (see
        # signature-form.js) and also to complete the signature after
        # the form is submitted (see method action()). This should not be
        # mistaken with the API access token.
        result = signature_starter.start_with_webpki()

        # The token acquired above can only be used for a single signature
        # attempt. In order to retry the signature it is necessary to get a
        # new token. This can be a problem if the user uses the back button of
        # the browser, since the browser might show a cached page that we
        # rendered previously, with a now stale token. To prevent this from
        # happening, we call the method get_expired_page_headers(). To prevent
        # this from happen, we force page expiration through HTTP headers to
        # prevent caching of the page.
        response = make_response(
            render_template('cades_signature_restpki/index.html',
                            token=result.token))

        get_expired_page_headers(response.headers)
        return response

    except Exception as e:
        return render_template('error.html', msg=e)
def complete():
    """

    This action will complete the authentication process and create a signature using a session
    token returned by user. Also, we recover the parameter "customState" containing the id of the
    file that will be signed.

    """
    try:
        # Recover variables from query parameters.
        code = request.args.get('code')
        state = request.args.get('state')

        # Get an instance of the TrustServiceManager class, responsible for communicating with 
        # PSCs and handling the OAuth flow.
        manager = TrustServicesManager()

        # Complete the authentication process, recovering the session info to be used on the
        # signature and the custom state (fileId).
        result = manager.complete_auth(code, state)

        # Recover file id on custom state parameter.
        file_id = result.custom_state

        # Verify if the provided file_id exists.
        file_path = join(current_app.config['APPDATA_FOLDER'], file_id)
        if not exists(file_path):
            return render_template('error.html', msg='File not found')

        # Get an instance of the PadesSigner class, responsible for receiving
        # the signature elements and performing the local signature.
        signer = PadesSigner()

        # Set PKI default options (see utils.py).
        set_pki_defaults(signer)

        # Set signature policy.
        signer.signature_policy = standard_signature_policies.PADES_BASIC_WITH_LTV

        # Set PDF to be signed.
        signer.set_pdf_to_sign_from_path(file_path)

        # Set trust session acquired on the following steps of this sample.
        signer.trust_service_session = result.session

        # Set a file reference for the stamp file. Note that this file can be
        # referenced later by "fref://{alias}" at the "url" field on the visual
        # representation (see content/vr.json or get_visual_representation()
        # method).
        signer.add_file_reference('stamp', get_pdf_stamp_path())

        # Set visual representation. We provide a dictionary that represents the
        # visual representation JSON model.
        signer.set_visual_representation(
            PadesVisualElementsExpress.get_visual_representation())

        # Generate path for output file and add to signer object.
        create_app_data()  # Guarantees that "app data" folder exists.
        output_file = '%s.pdf' % (str(uuid.uuid4()))
        signer.output_file = join(current_app.config['APPDATA_FOLDER'], output_file)

        # Perform the signature.
        signer_cert = signer.sign(get_cert=False)

        response = make_response(render_template(
            'pades_cloud_oauth_express/signature-info.html',
            signed_pdf=output_file))
        get_expired_page_headers(response.headers)

        return response

    except Exception as e:
        return render_template('error.html', msg=e)
Example #9
0
def index(userfile=None):
    """

    This function initiates a PAdES signature using REST PKI and renders the
    signature page.

    Both PAdES signature examples, with a server file and with a file uploaded
    by the user, converge to this function. The difference is that, when the
    file is uploaded by the user, the function is called with a URL argument
    named "userfile".

    """

    try:

        # Get an instantiate of the PadesSignatureStarter class, responsible for
        # receiving the signature elements and start the signature process.
        signature_starter = PadesSignatureStarter(get_restpki_client())

        # If the URL argument "userfile" is filled, it means the user was
        # redirected here by "upload" view (signature with file uploaded by
        # user). We'll set the path of the file to be signed, which was saved
        # in the app_data folder by "upload" view.
        if userfile is not None:
            signature_starter.set_pdf_to_sign(
                '%s/%s' % (current_app.config['APPDATA_FOLDER'], userfile))
        else:
            signature_starter.set_pdf_to_sign(get_sample_doc_path())

        # Set the signature policy.
        signature_starter.signature_policy =\
            StandardSignaturePolicies.PADES_BASIC

        # Set a security context to be used to determine trust in the
        # certificate chain. We have encapsulated the security context choice on
        # util.py.
        signature_starter.security_context = get_security_context_id()

        # Set the visual representation for the signature. We have encapsulated
        # this code (on util-pades.py) to be used on various PAdES examples.
        signature_starter.visual_representation = get_visual_representation()

        # Call the start_with_webpki() method, which initiates the signature.
        # This yields the token, a 43-character case-sensitive URL-safe string,
        # which identifies this signature process. We'll use this value to call
        # the signWithRestPki() method on the Web PKI component (see
        # signature-form.js javascript) and also to complete the signature after
        # the form is submitted (see method pades_signature_action()). This
        # should not be mistaken with the API access token.
        result = signature_starter.start_with_webpki()

        # The token acquired above can only be used for a single signature
        # attempt. In order to retry the signature it is necessary to get a new
        # token. This can be a problem if the user uses the back button of the
        # browser, since the browser might show a cached page that we rendered
        # previously, with a now stale token. To prevent this from happen, we
        # force page expiration through HTTP headers to prevent caching of the
        # page.
        response = make_response(render_template('pades_signature/index.html',
                                                 token=result.token,
                                                 userfile=userfile))
        response.headers = get_expired_page_headers()
        return response

    except Exception as e:
        return render_template('error.html', msg=e)
Example #10
0
def authorize(file_id):
    """"

    This action is called after the form after the user press the button "Sign". 
    This action will receive the user's CPF and current password.

    """
    try:
        # Recover variables from the POST arguments.
        cpf = request.form['cpf']
        service = request.form['service']
        password = request.form['password']

        # Process cpf, removing all formatting.
        plainCpf = cpf.replace(".", "").replace("-", "")

        # Get an instance of the TrustServiceManager class, responsible for communicating with 
        # PSCs and handling the password flow.
        manager = TrustServicesManager()

        # Complete authentication using CPF and current password. The following method has three sessionTypes:
        # - SINGLE_SIGNATURE: The returned token can only be used for one single signature request.
        # - MULTI_SIGNATURE: The returned token can only be used for one multi signature request.
        # - SIGNATURE_SESSION: The return token can only be used for one or more signature requests.
        result = manager.password_authorize(service, plainCpf, password, trust_service_session_types.SIGNATURE_SESSION)

        # Verify if the provided file_id exists.
        file_path = join(current_app.config['APPDATA_FOLDER'], file_id)
        if not exists(file_path):
            return render_template('error.html', msg='File not found')
        
        # Get an instance of the PadesSigner class, responsible for receiving
        # the signature elements and performing the local signature.
        signer = PadesSigner()

        # Set PKI default options (see utils.py).
        set_pki_defaults(signer)

        # Set signature policy.
        signer.signature_policy = standard_signature_policies.PADES_BASIC_WITH_LTV

        # Set PDF to be signed.
        signer.set_pdf_to_sign_from_path(file_path)

        # Set trust session acquired on the following steps of this sample.
        signer.trust_service_session = result.session

        # Set a file reference for the stamp file. Note that this file can be
        # referenced later by "fref://{alias}" at the "url" field on the visual
        # representation (see content/vr.json or get_visual_representation()
        # method).
        signer.add_file_reference('stamp', get_pdf_stamp_path())

        # Set visual representation. We provide a dictionary that represents the
        # visual representation JSON model.
        signer.set_visual_representation(
            PadesVisualElementsExpress.get_visual_representation())

        # Generate path for output file and add to signer object.
        create_app_data()  # Guarantees that "app data" folder exists.
        output_file = '%s.pdf' % (str(uuid.uuid4()))
        signer.output_file = join(current_app.config['APPDATA_FOLDER'], output_file)

        # Perform the signature.
        signer_cert = signer.sign(get_cert=False)

        response = make_response(render_template(
            'pades_cloud_pwd_express/signature-info.html',
            signed_pdf=output_file))
        get_expired_page_headers(response.headers)

        return response

    except Exception as e:
        return render_template('error.html', msg=e)