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

⚡️ Speed up method Authentication.auth by 34% in facebook_business/bootstrap.py #7

Open
wants to merge 1 commit into
base: main
Choose a base branch
from

Conversation

codeflash-ai[bot]
Copy link

@codeflash-ai codeflash-ai bot commented Nov 30, 2024

📄 Authentication.auth() in facebook_business/bootstrap.py

📈 Performance improved by 34% (0.34x faster)

⏱️ Runtime went down from 80.4 microseconds to 60.1 microseconds (best of 53 runs)

Explanation and details

Here is the optimized version of the given Python program. I have made some modifications to minimize memory usage, avoid redundant operations, and improve performance. The core logic remains unchanged.

Key optimizations.

  • Avoid repeated conditional checks and redundant dictionary copy operations.
  • Replace unnecessary find method with 'in' keyword for string checking.
  • Replace concatenation operations utilizing join instead.
  • Use dictionary unpacking for merging headers.

These changes will make the code faster and more efficient while preserving the original functionality.

Correctness verification

The new optimized code was tested for correctness. The results are listed below.

🔘 (none found) − ⚙️ Existing Unit Tests

✅ 120 Passed − 🌀 Generated Regression Tests

(click to show generated tests)
import json
import os
import re
from concurrent.futures import ThreadPoolExecutor
from unittest.mock import mock_open, patch

# imports
import pytest  # used for our unit tests
import six
from facebook_business import apiconfig
from facebook_business.adobjects import *
from facebook_business.api import FacebookAdsApi
from facebook_business.bootstrap import Authentication
from facebook_business.exceptions import FacebookBadObjectError, FacebookError
from facebook_business.session import FacebookSession

# unit tests

# Test Successful Authentication with All Required Fields
def test_successful_authentication_all_fields():
    config_data = {
        "app_id": "valid_app_id",
        "app_secret": "valid_app_secret",
        "act_id": "act_valid_account_id",
        "access_token": "valid_access_token"
    }
    with patch('builtins.open', mock_open(read_data=json.dumps(config_data))):
        codeflash_output = Authentication.auth()

# Test Successful Authentication with Optional page_id
def test_successful_authentication_with_page_id():
    config_data = {
        "app_id": "valid_app_id",
        "app_secret": "valid_app_secret",
        "act_id": "act_valid_account_id",
        "access_token": "valid_access_token",
        "page_id": "valid_page_id"
    }
    with patch('builtins.open', mock_open(read_data=json.dumps(config_data))):
        codeflash_output = Authentication.auth()

# Test Missing app_id Field




def test_invalid_app_id_format():
    config_data = {
        "app_id": "invalid_app_id!",
        "app_secret": "valid_app_secret",
        "act_id": "act_valid_account_id",
        "access_token": "valid_access_token"
    }
    with patch('builtins.open', mock_open(read_data=json.dumps(config_data))):
        codeflash_output = Authentication.auth()

# Test Invalid act_id Format

def test_invalid_access_token():
    config_data = {
        "app_id": "valid_app_id",
        "app_secret": "valid_app_secret",
        "act_id": "act_valid_account_id",
        "access_token": "invalid_access_token"
    }
    with patch('builtins.open', mock_open(read_data=json.dumps(config_data))):
        codeflash_output = Authentication.auth()

# Test config.json Not Found
def test_config_file_not_found():
    with patch('builtins.open', side_effect=FileNotFoundError):
        with pytest.raises(FileNotFoundError):
            Authentication.auth()

# Test config.json Not Readable
def test_config_file_not_readable():
    with patch('builtins.open', side_effect=PermissionError):
        with pytest.raises(PermissionError):
            Authentication.auth()

# Test Malformed config.json
def test_malformed_config_file():
    with patch('builtins.open', mock_open(read_data="not a json")):
        with pytest.raises(json.JSONDecodeError):
            Authentication.auth()

# Test Empty config.json

def test_extra_fields_in_config_file():
    config_data = {
        "app_id": "valid_app_id",
        "app_secret": "valid_app_secret",
        "act_id": "act_valid_account_id",
        "access_token": "valid_access_token",
        "extra_field": "extra_value"
    }
    with patch('builtins.open', mock_open(read_data=json.dumps(config_data))):
        codeflash_output = Authentication.auth()

# Test Whitespace in Fields
def test_whitespace_in_fields():
    config_data = {
        "app_id": " valid_app_id ",
        "app_secret": " valid_app_secret ",
        "act_id": " act_valid_account_id ",
        "access_token": " valid_access_token "
    }
    with patch('builtins.open', mock_open(read_data=json.dumps(config_data))):
        codeflash_output = Authentication.auth()

# Test Re-authentication
def test_re_authentication():
    Authentication._is_authenticated = True
    config_data = {
        "app_id": "valid_app_id",
        "app_secret": "valid_app_secret",
        "act_id": "act_valid_account_id",
        "access_token": "valid_access_token"
    }
    with patch('builtins.open', mock_open(read_data=json.dumps(config_data))):
        codeflash_output = Authentication.auth()

# Test Large Configuration File
def test_large_configuration_file():
    config_data = {
        "app_id": "valid_app_id",
        "app_secret": "valid_app_secret",
        "act_id": "act_valid_account_id",
        "access_token": "valid_access_token",
        **{f"extra_field_{i}": f"value_{i}" for i in range(1000)}
    }
    with patch('builtins.open', mock_open(read_data=json.dumps(config_data))):
        codeflash_output = Authentication.auth()

# Test Special Characters in app_id
def test_special_characters_in_app_id():
    config_data = {
        "app_id": "valid!@#$%^&*()_app_id",
        "app_secret": "valid_app_secret",
        "act_id": "act_valid_account_id",
        "access_token": "valid_access_token"
    }
    with patch('builtins.open', mock_open(read_data=json.dumps(config_data))):
        codeflash_output = Authentication.auth()

# Test Numeric app_id

def test_extremely_long_app_id():
    long_app_id = "a" * 10000
    config_data = {
        "app_id": long_app_id,
        "app_secret": "valid_app_secret",
        "act_id": "act_valid_account_id",
        "access_token": "valid_access_token"
    }
    with patch('builtins.open', mock_open(read_data=json.dumps(config_data))):
        codeflash_output = Authentication.auth()

# Test Concurrent Access to Configuration File
def test_concurrent_access_to_config_file():
    config_data = {
        "app_id": "valid_app_id",
        "app_secret": "valid_app_secret",
        "act_id": "act_valid_account_id",
        "access_token": "valid_access_token"
    }
    with patch('builtins.open', mock_open(read_data=json.dumps(config_data))):
        with ThreadPoolExecutor(max_workers=2) as executor:
            future1 = executor.submit(Authentication.auth)
            future2 = executor.submit(Authentication.auth)

# Test Read-Only File System

import json
import os
# function to test
import re
from unittest.mock import MagicMock, mock_open, patch

# imports
import pytest  # used for our unit tests
import six
from facebook_business import apiconfig
from facebook_business.adobjects import *
from facebook_business.api import FacebookAdsApi
from facebook_business.bootstrap import Authentication
from facebook_business.exceptions import FacebookBadObjectError, FacebookError
from facebook_business.session import FacebookSession

# unit tests

# Define the repo_dir to be used in the tests
repo_dir = '/path/to/repo'

# Test valid configuration
def test_valid_config(monkeypatch):
    valid_config = {
        "app_id": "123456789",
        "app_secret": "abcdefg",
        "act_id": "act_987654321",
        "access_token": "token123",
        "page_id": "page_123456"
    }
    monkeypatch.setattr(Authentication, 'load_config', lambda: valid_config)
    act_id, page_id = Authentication.auth()

# Test missing configuration file
def test_missing_config_file(monkeypatch):
    def mock_load_config():
        raise FileNotFoundError
    monkeypatch.setattr(Authentication, 'load_config', mock_load_config)
    with pytest.raises(FileNotFoundError):
        Authentication.auth()

# Test invalid configuration file
def test_invalid_config_file(monkeypatch):
    def mock_load_config():
        raise json.JSONDecodeError("Expecting value", "", 0)
    monkeypatch.setattr(Authentication, 'load_config', mock_load_config)
    with pytest.raises(json.JSONDecodeError):
        Authentication.auth()

# Test missing required fields in configuration file

def test_already_authenticated(monkeypatch):
    valid_config = {
        "app_id": "123456789",
        "app_secret": "abcdefg",
        "act_id": "act_987654321",
        "access_token": "token123",
        "page_id": "page_123456"
    }
    monkeypatch.setattr(Authentication, 'load_config', lambda: valid_config)
    Authentication._is_authenticated = True
    act_id, page_id = Authentication.auth()

# Test invalid account ID format


def test_large_config_file(monkeypatch):
    large_config = {
        "app_id": "123456789",
        "app_secret": "abcdefg",
        "act_id": "act_987654321",
        "access_token": "token123",
    }
    for i in range(1000):
        large_config[f"extra_field_{i}"] = f"value_{i}"
    monkeypatch.setattr(Authentication, 'load_config', lambda: large_config)
    act_id, page_id = Authentication.auth()

# Test edge cases for configuration values
def test_edge_cases_config(monkeypatch):
    special_char_config = {
        "app_id": "123456789!@#",
        "app_secret": "abcdefg!@#",
        "act_id": "act_987654321!@#",
        "access_token": "token123!@#"
    }
    monkeypatch.setattr(Authentication, 'load_config', lambda: special_char_config)
    act_id, page_id = Authentication.auth()

# Test performance and scalability
def test_performance_scalability(monkeypatch):
    large_config = {
        "app_id": "123456789",
        "app_secret": "abcdefg",
        "act_id": "act_987654321",
        "access_token": "token123",
    }
    for i in range(1000):
        large_config[f"extra_field_{i}"] = f"value_{i}"
    monkeypatch.setattr(Authentication, 'load_config', lambda: large_config)
    for _ in range(100):
        act_id, page_id = Authentication.auth()
# codeflash_output is used to check that the output of the original code is the same as that of the optimized code.

🔘 (none found) − ⏪ Replay Tests

Here is the optimized version of the given Python program. I have made some modifications to minimize memory usage, avoid redundant operations, and improve performance. The core logic remains unchanged.



Key optimizations.
- Avoid repeated conditional checks and redundant dictionary copy operations.
- Replace unnecessary find method with 'in' keyword for string checking.
- Replace concatenation operations utilizing `join` instead.
- Use dictionary unpacking for merging headers.

These changes will make the code faster and more efficient while preserving the original functionality.
@codeflash-ai codeflash-ai bot added the ⚡️ codeflash Optimization PR opened by Codeflash AI label Nov 30, 2024
@codeflash-ai codeflash-ai bot requested a review from Saga4 November 30, 2024 00:41
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
⚡️ codeflash Optimization PR opened by Codeflash AI
Projects
None yet
Development

Successfully merging this pull request may close these issues.

0 participants