Sly32

Рейтинг
367
Регистрация
29.03.2012
не хаос #:
Дача это свой мир, непосвященным в этот процесс ничего не понять и их там не ждут.

Ага, мир обгорелых на солнце задниц и белых животов, мошек, кротов на лужайках, черных ногтях, запаха навоза, горелого мяса, водки)))
Если что это шутка - это действительно другой мир и это надо любить. Мне понадобилось 17 лет чтобы понять что это не мое, хотя покупалась с мыслью проводить пенсию на свежем воздухе.

alaev #:
На велосипеде въехать в яму неравнозначно попаданию одного колеса автомобиля в яму. Учи физику!!!

Я в последний раз, чукча тебе пытаюсь обьяснить!!! Мы не сравниваем автомобиль и велосипед, автобус, танк, 6-осный грузовик или легковушку.
Разговор для разницы нагрузку на подвеску при проезде ямы на разной скорости одного типа  транспортного средства

На велике ты кульнешься в яму на скорости, автомобиль ее не заметит. Но сила удара по подвеске будет разной!!
А на определенной скорости колесо просто перелетит яму, вообще не получив удара! Это был вопрос Дмитрия и мои ответы основываются на нем. А не на ПДД, аэродинамике и прочей белиберде что ты приплел. 

Если уж и этот текст ты не в состоянии прочитать - умываю руки, медицина тут бессильна.

Vladimir #:
Дача это диагноз...для поясницы. Впрочем как и гири)

с 2005 года все лето проводил на даче. Если выходные, то в пятницу заехал, в воскр - вернулся. С утра корячишься на огороде, ругаешься с тещей, когда она выкопала яму на твоей лужайке или под гамаком посадила морковку. Вечером баня и обжирание горелым мясом. Пару раз удается выбраться по грибы... Обычно приезжаешь в воскресенье замордованый по самое не хочу. А, забыл про еще одно наказание - урожай. Сначала пытаешься вырастить, потом придумать - как его сохранить))) Сутками катать помидоры-огурцы, кабаки сок.... Брр
После переезда понял, что свободное время можно проводить поинтереснее. Поехать в парк, лес, горы, на экскурсию. Перекусить в кафешке чем-нибудь интересным. Сходить в Термы-спа. Вернуться отдохнувшим.
Поэтому продал этот вид "отдыха". Конечно, иногда ностальгия мучает, но в целом - без нее лучше.

Vladimir SEO #:
Почему прогу можно красть а картошку нет? И то и другое делал человек,  тратил силы время. 

капер Дмитрий этого искренне не понимает. У него все приводится к логике - "Зачем покупать, если можно своровать?" и борьбе с корпорациями.
Хотя вчера меня выбесил нетфликс, когда я заметил, что в базовую подписку теперь включен только HD контент.
За 4К будь добр, доплати еще пару долларов в месяц. Дмитро, помоги, выкачай последние релизы в 4К и пришли мне на флешке))) Ты же Робин Гут к тому же, должен помочь прозябающей еуропе)

sumpsonb #:
а что не так?

Для начала:

parser/index_api.py:1:1: F401 'json' imported but unused
parser/index_api.py:4:1: F401 'datetime.datetime' imported but unused
parser/index_api.py:9:1: E302 expected 2 blank lines, found 1
parser/index_api.py:13:1: W293 blank line contains whitespace
parser/index_api.py:14:1: W293 blank line contains whitespace
parser/index_api.py:15:9: E303 too many blank lines (2)
parser/index_api.py:22:1: W293 blank line contains whitespace
parser/index_api.py:23:1: W293 blank line contains whitespace
parser/index_api.py:24:9: E303 too many blank lines (2)
parser/index_api.py:36:1: W293 blank line contains whitespace
parser/index_api.py:38:30: F541 f-string is missing placeholders
parser/index_api.py:40:1: W293 blank line contains whitespace
parser/index_api.py:47:1: W293 blank line contains whitespace
parser/index_api.py:52:1: W293 blank line contains whitespace
parser/index_api.py:56:1: W293 blank line contains whitespace
parser/index_api.py:59:64: W504 line break after binary operator
parser/index_api.py:59:67: W291 trailing whitespace
parser/index_api.py:60:71: W504 line break after binary operator
parser/index_api.py:60:74: W291 trailing whitespace
parser/index_api.py:61:21: E129 visually indented line with same indent as next logical line
parser/index_api.py:71:1: W293 blank line contains whitespace
parser/index_api.py:80:1: W293 blank line contains whitespace
parser/index_api.py:84:1: W293 blank line contains whitespace
parser/index_api.py:88:1: W293 blank line contains whitespace
parser/index_api.py:90:1: W293 blank line contains whitespace
parser/index_api.py:93:1: W293 blank line contains whitespace
parser/index_api.py:99:30: W291 trailing whitespace
parser/index_api.py:100:1: W293 blank line contains whitespace
parser/index_api.py:101:1: W293 blank line contains whitespace
parser/index_api.py:102:13: E303 too many blank lines (2)
parser/index_api.py:108:1: W293 blank line contains whitespace
parser/index_api.py:110:1: W293 blank line contains whitespace
parser/index_api.py:114:1: E305 expected 2 blank lines after class or function definition, found 1
parser/index_api.py:119:1: W293 blank line contains whitespace
parser/index_api.py:121:27: W292 no newline at end of file

Это арбнет может позволить себе писать не соблюдая кодстайл и не думая как там потом интерпретатор будет корячится. Правда, допускаю что что-то из этого - из-за ошибки копирования.
Теперь по замечаниям:
- Логгер не нужно пихать в класс - это нарушает бизнес логику, не дает его переиспользовать,  возникаю сложности с тестированием. 
- Хорошая практика обьявлять сессию как контекст-менеджер. Нужно обьяснять зачем? 
- один метод - одно действие. вспоминаем SOLID. поэтому разбиваем process_urls. В черновом варианте примерно так:

import json
import time
import logging
from datetime import datetime
from google.oauth2 import service_account
from google.auth.transport.requests import AuthorizedSession
import os
from contextlib import contextmanager
from typing import List, Tuple, Optional

def setup_logger(name: str, log_file: str) -> logging.Logger:
    """Configure and return a logger with file and console handlers."""
    logger = logging.getLogger(name)
    logger.setLevel(logging.INFO)
    
    if not logger.handlers:
        # File handler
        file_handler = logging.FileHandler(log_file)
        file_handler.setFormatter(
            logging.Formatter('[%(asctime)s] [%(levelname)s] %(message)s',
                            datefmt='%Y-%m-%d %H:%M:%S')
        )
        logger.addHandler(file_handler)
        
        # Console handler
        console_handler = logging.StreamHandler()
        console_handler.setFormatter(
            logging.Formatter('[%(asctime)s] [%(levelname)s] %(message)s')
        )
        logger.addHandler(console_handler)
    
    return logger

class GoogleIndexingAPI:
    def __init__(self, service_account_file: str, urls_file: str, logger: logging.Logger):
        self.service_account_file = service_account_file
        self.urls_file = urls_file
        self.logger = logger

    @contextmanager
    def get_authenticated_session(self):
        """Context manager for handling authenticated sessions."""
        try:
            credentials = service_account.Credentials.from_service_account_file(
                self.service_account_file,
                scopes=['https://www.googleapis.com/auth/indexing']
            )
            session = AuthorizedSession(credentials)
            self.logger.info("Successfully authenticated with service account")
            yield session
        except Exception as e:
            self.logger.error(f"Authentication failed: {str(e)}")
            yield None
        finally:
            if session:
                session.close()

    def submit_url(self, session: AuthorizedSession, url: str) -> bool:
        """Submit a single URL for indexing."""
        api_url = 'https://indexing.googleapis.com/v3/urlNotifications:publish'
        data = {'url': url, 'type': 'URL_UPDATED'}
        
        try:
            self.logger.info(f"Submitting URL to index: {url}")
            response = session.post(api_url, json=data)
            
            if response.status_code == 200:
                response_data = response.json()
                if self._validate_response(response_data, url):
                    self.logger.info(f"Successfully submitted URL: {url}")
                    return True
            
            self.logger.error(f"Failed to submit URL {url}. Status: {response.status_code}")
            return False
            
        except Exception as e:
            self.logger.error(f"Error submitting URL {url}: {str(e)}")
            return False

    def _validate_response(self, response_data: dict, url: str) -> bool:
        """Validate the API response data."""
        return ('urlNotificationMetadata' in response_data and
                'url' in response_data['urlNotificationMetadata'] and
                response_data['urlNotificationMetadata']['url'] == url)

    def _read_urls(self) -> List[str]:
        """Read URLs from file."""
        with open(self.urls_file, 'r') as f:
            return [line.strip() for line in f if line.strip()]

    def _save_failed_urls(self, failed_urls: List[str]) -> None:
        """Save failed URLs to file."""
        if failed_urls:
            failed_file = 'failed_urls.txt'
            with open(failed_file, 'w') as f:
                for url in failed_urls:
                    f.write(f"{url}\n")
            self.logger.info(f"Failed URLs written to {failed_file}")

    def process_urls(self) -> Tuple[int, int]:
        """Process all URLs from the input file."""
        if not os.path.exists(self.urls_file):
            self.logger.error(f"URLs file not found: {self.urls_file}")
            return (0, 0)
            
        try:
            urls = self._read_urls()
            self.logger.info(f"Found {len(urls)} URLs to process")
            
            successful_urls = []
            failed_urls = []
            
            with self.get_authenticated_session() as session:
                if not session:
                    return (0, 0)
                
                for url in urls:
                    if self.submit_url(session, url):
                        successful_urls.append(url)
                    else:
                        failed_urls.append(url)
                    time.sleep(1)
            
            self._save_failed_urls(failed_urls)
            self.logger.info(f"Processing complete. Success: {len(successful_urls)}, Failed: {len(failed_urls)}")
            return len(successful_urls), len(failed_urls)
            
        except Exception as e:
            self.logger.error(f"Error processing URLs: {str(e)}")
            return (0, 0)

def main():
    # Configuration
    SERVICE_ACCOUNT_FILE = "service-account.json"
    URLS_FILE = "urls.txt"
    LOG_FILE = "indexing.log"
    
    # Setup logger
    logger = setup_logger("google_indexing", LOG_FILE)
    
    # Initialize and run indexer
    indexer = GoogleIndexingAPI(SERVICE_ACCOUNT_FILE, URLS_FILE, logger)
    success, failed = indexer.process_urls()
    
    return success, failed

if __name__ == "__main__":
    main()

Ну и работать со сторонним апи в синхронном коде я бы вообще не стал. Использование threading ускорит работу минимум в 4 раза. 
это все так, навскидку. Если повозиться, можно еще пооптимизировать. 

alaev #:
Сила притяжения действует всегда,

Где я тебя спрашивал про силу притяжения? Понимаю, что тебе сложно сосредоточится, поэтому напоминаю - разговор был про ускорение свободного падения - для тела не имеющего опоры.

alaev #:
У тебя с пониманием разделов физики плохо.

Я теперь полностью уверен, что ты врешь про институты. Ты вообще не понимаешь о чем идет речь. Какая подьемная сила будет у колеса, катящегося по дороге? Разберись уже, когда она возникает, двоечник.

Какая подьемная сила может быть у пули? Почитай в принципе, что это такое, раз уж приплел. Не понимаю, как можно быть настолько...
Ты идешь по дороге и пялишься в тик-ток и вдруг яма - ты что - перелетишь ее используя подьемную силу? 
ты ... упадешь на дно. Если  ты шел медленно, прямо у края ямы и рухнешь, со стороны откуда шел. Если довольно быстро - упадешь ближе к дальнему краю. Если ты бежал стелефоном в руках, чего обычно люди не делают, но от тебя можно всего ожидать - ты возможно и не упадешь а повиснешь на другой стороне или даже перепрыгнешь(сомневаюсь)
Уже даже интересно, дойдет ли это до тебя или дальше будешь бред из нейросетей постить?

alaev #:
Ускорение свободного падения, как ты говоришь, "действовать" не начинает, оно всегда действовало. И на колесо, и на глушак

Да ладно? То есть ты сидишь в кресле и падаешь? с какой скоростью? Или все-таки ты начинаешь падать, когда под тобой нет опоры? 

Ну может давай к баллистике перейдем? Что происходит с пулей, когда она вылетает из ствола? Чтоб не было вопросов - ствол расположен горизонально? Крыльев у пули нет) Двигателя нет. Она будет взлетать или падать? 
От начальной скорости зависит, сколько она пролетит?
Никакого отношения центр масс к данной задаче не имеет. Гуглишь и сам не понимаешь что))) 

alaev #:

Ты тут словоблудием занят.

Скорость - вектор. И силы, действующие на авто, тоже векторные величины.

В школе это объясняют.

Но в школе не изучают взаимодействие вращающегося колеса с неподвижным препятствием.

Я уже сомневаюсь, что ты даже в школе учился... Не можешь понять элементарное. Давай я тебе как для восьмиклассника обьясню. Что такое скорость - знаешь? За сколько ты сможешь проехать, например 50 см сможешь высчитать? Дальше. Что такое ускорение свободного падения знаешь? Если нет то почитай. Когда колесо теряет опору, что на него начинает действовать? Ускорение свободного падения. Форумлу расчета знаешь?
А теперь ты знаешь, что за Х секунд ты проедешь А метров. При этом за эти же Х секунд колесо провалится в них тоже на В метров. Соответственно на выезде из ямы для колеса образуется условное препятствие в С метров высотой.  Следишь за логикой или уже пошел пасьянс раскладывать? Теперь простая задача - если скорость будет в 2 раза выше, сможешь посчитать, насколько времени тебе понадобиться меньше, чтобы проехать те же А метров? И Высота С изменится или нет и соответственно удар по подвеске. 
А теперь скажи мне каким боком тут марка автомобиля, вращение колеса... Понимаешь что в данном случае это константы, которые вообще не важны?

Сомневаюсь, конечно что до тебя дошло. Любопытно посмотреть как будешь выкручиваться тут. Примешаешь качество дорог в Польше?

alaev #:
Я на скорости 100 км/ч ночью вовремя не заметил колесо на МКАДе и наехал на него

Ну правильно, чего жалеть мамкину вольву)))😂

sigiziy #:
Либо план Б - очень медленно без буханий. Промежуточные варианты неприемлемы.

Вообще-то как по мне - самый правильны вариант) Если конечно колесо достает до дна ямы) Но иначе это уже каскадерство. Проще обьехать

Сергей про е-ком #:
Но размер ямы имеет значение в таком случае, как и диаметр колеса.

Конечно имеет. Как у прыгуна - чем быстрее разгонишься, тем дальше прыгнешь. Так и тут есть определенная скорость, двигаясь с которой ты не ударишься колесом о край ямы а просто перелетишь ее. 

Повторюсь - разговор только о том работает ли принцип "Выше скорость - меньше яма"  Понятно что можно учитывать дополнительно массу параметров - подвеска, горизонтальность движения,  масса автомобиля, сопротивление воздуха и тд. 

Простая формула за 8-й класс )))

Всего: 7117