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

[ERROR] 'NoneType' object has no attribute 'span' #1498

Closed
hojinYang opened this issue Mar 16, 2023 · 50 comments · Fixed by duvu/pytube#1 or rgryta/pytube#5 · May be fixed by #1501
Closed

[ERROR] 'NoneType' object has no attribute 'span' #1498

hojinYang opened this issue Mar 16, 2023 · 50 comments · Fixed by duvu/pytube#1 or rgryta/pytube#5 · May be fixed by #1501
Labels

Comments

@hojinYang
Copy link

Hi!

I'm using the latest version, and it worked well until a few days ago. but I got this error today many times while downloading some youtube videos.

I looked into this issue pages and I suspect this is a recurring issue when google changes the js file from their end. I would appreciate it if anyone could provide a solution. Thanks!

File "/usr/local/lib/python3.8/dist-packages/pytube/cipher.py", line 360, in get_throttling_plan', ' raw_code = get_throttling_function_code(js)', ' File "/usr/local/lib/python3.8/dist-packages/pytube/cipher.py", line 277, in get_throttling_function_code', " code_lines_list = find_object_from_startpoint(js, match.span()[1]).split('\n')", "AttributeError: 'NoneType' object has no attribute 'span'"]

@hojinYang hojinYang added the bug label Mar 16, 2023
@github-actions
Copy link

Thank you for contributing to PyTube. Please remember to reference Contributing.md

@Neirno
Copy link

Neirno commented Mar 16, 2023

Same erorre

@Carlolopespesia
Copy link

Same error

@L-Lawliet27
Copy link

Hi,

I also have the same error, which is weird because it was working fine this entire week, as well as about 30-45 minutes ago.

@mattdev-sh
Copy link

I tried using a solution in another similar topic issue, changing get_throttling_function_name in cipher.py , but it did not work.

Probably something changed on the youtube side.

@katestephens
Copy link

This was working for me up until about an hour ago or so... Did YouTube release a change that brought back the regex issue from last year?

@WeAreNot
Copy link

WeAreNot commented Mar 16, 2023

Same thing happen with me :)
it was happen from 00:00 to 00:15 (Moscow, +3)

@Magic-Harp
Copy link

Same thing here, stopped working overnight!

@RichardeLira
Copy link

The same error occurs here. I tested it around 2 pm (Brasilia time) and it was working perfectly. Now around 6 pm (Brasilia time) it stopped working.

@yasntrk
Copy link

yasntrk commented Mar 16, 2023

Same

@andrii1
Copy link

andrii1 commented Mar 16, 2023

Same error...

@stanislawleguta85
Copy link

Same error

@glubsy
Copy link
Contributor

glubsy commented Mar 16, 2023

Everyone please stop posting "+1" or "same error".
Either publish a patch and open a merge request, or refrain from posting.

@SeoJeongguk
Copy link

SeoJeongguk commented Mar 16, 2023

same error too ㅠㅠ

something was changed again at Youtube side

I tried change func_regex = re.compile(r"function([^)]+)") in parser.py file and
name = re.escape(get_throttling_function_name(js)) to name="iha" at cyper.py

but don't work

@Von31
Copy link

Von31 commented Mar 17, 2023

Same error! :'(

@EchterAlsFake
Copy link

Hello Guys.

I just asked ChatGPT (4) about this Issue and ChatGPT said, that we need to update the regular expression in the get_throttling_function_name... function, so that it can analyze the YouTube Java Script file. It has something to do with the base.js file. I am not so familiar with java script (actually I don't know anything), so I can't extract the new regular expression from that base.js file. It has more than 120000 lines by the way. I hope that anyone who understands Java Script can do something with that Information and update the regular expression in the python file.

@RichardeLira
Copy link

Hello Guys.

I just asked ChatGPT (4) about this Issue and ChatGPT said, that we need to update the regular expression in the get_throttling_function_name... function, so that it can analyze the YouTube Java Script file. It has something to do with the base.js file. I am not so familiar with java script (actually I don't know anything), so I can't extract the new regular expression from that base.js file. It has more than 120000 lines by the way. I hope that anyone who understands Java Script can do something with that Information and update the regular expression in the python file.

Do you know where this base.js file is?

@dark9ive
Copy link

dark9ive commented Mar 17, 2023

I just patched this error by simply modifying {home}/.local/lib/python3.7/site-packages/pytube/cipher.py
Line 411

transform_plan_raw = find_object_from_startpoint(raw_code, match.span()[1] - 1)

to

transform_plan_raw = js

And everything works fine.
Hope this can solve your problem.

@MeaningOf42
Copy link

Can you put in a pull request for that please?

@RichardeLira
Copy link

I just patched this error by simply modifying {home}/.local/lib/python3.7/site-packages/pytube/cipher.py Line 411

transform_plan_raw = find_object_from_startpoint(raw_code, match.span()[1] - 1)

to

transform_plan_raw = js

And everything works fine. Hope this can solve your problem.

Thank you very much! It worked perfectly here. I have no idea how this change fixed the bug (if you want to explain that would be great), but it worked perfectly anyway.

@JLeopolt
Copy link

I just patched this error by simply modifying {home}/.local/lib/python3.7/site-packages/pytube/cipher.py Line 411

transform_plan_raw = find_object_from_startpoint(raw_code, match.span()[1] - 1)

to

transform_plan_raw = js

And everything works fine. Hope this can solve your problem.

Hello, can you please create a pull request for this fix? Thank you for figuring it out :)

@dark9ive
Copy link

dark9ive commented Mar 17, 2023

I just patched this error by simply modifying {home}/.local/lib/python3.7/site-packages/pytube/cipher.py Line 411

transform_plan_raw = find_object_from_startpoint(raw_code, match.span()[1] - 1)

to

transform_plan_raw = js

And everything works fine. Hope this can solve your problem.

Thank you very much! It worked perfectly here. I have no idea how this change fixed the bug (if you want to explain that would be great), but it worked perfectly anyway.

TBH, I have no idea why this works.
Just poke around the codes and it works like a miracle.
My discord bot just crashed because of this bug, right before I'm going to sleep. So I guess I'll leave this work to someone else who has the passion to do so.

JLeopolt added a commit to JLeopolt/pytube that referenced this issue Mar 17, 2023
Resolves pytube#1498 by modifying 'cipher.py' line 411 to "transform_plan_raw = js". pytube#1498
All credit goes to https://github.com/dark9ive for fixing the issue.
@JLeopolt
Copy link

I have opened a pull request which should solve this issue. Credit to @dark9ive for the fix.

@dark9ive
Copy link

dark9ive commented Mar 17, 2023

I have opened a pull request which should solve this issue. Credit to @dark9ive for the fix.

Thanks for your help.

BTW, I think I can give a simple explain about how I find this solution.
You can see that transform_plan_raw will be filtered by step_start = r"c\[(\d+)\]\(c\[(\d+)\](,c(\[(\d+)\]))?\)" in line 416. I downloaded the full js file and grep it on my own, and found that this pattern only matches once. So I guess put the whole file into regex filter may work.

Fortunately it works, otherwise I would have to sleep 1 or 2 hours less.

@Shakal1105
Copy link

ty for bug
now Youtube use old js write with new integrations

on
transform_plan_raw = js

workiing because we got gull js code and regix got our streams
i do not write pytube but this bug solved

close the topic

@realizecondition
Copy link

Hi,

So I did pip uninstall pytube, and then pip install pytube. Nothing changed at all to fix this error.

I had to go into the source code myself and make that change on line 411. I had to find that file cypher.py in "%localappdata%/programs/python/python310/lib/site-packages/pytube" and navigate to line 411 and comment out "transform_plan_raw = find_object_from_startpoint(raw_code, match.span()[1] - 1)" and set it to "transform_plan_raw = js" myself manually.

What process should I have done to update and fix the error efficiently? Or was it the right process but this error fix is not yet "official"?

@cs20131516
Copy link

In my case, i am working on collab, but it doesn't work.

alexerhardt added a commit to alexerhardt/pytube that referenced this issue Mar 19, 2023
Monkey patching due to bug found by the community:
pytube#1498 (comment)
@wambugu71
Copy link

Same error anyone who have known how to fix it

@wambugu71
Copy link

Thats it , it worked .... 👍

@NicolasTr
Copy link

One line fix based on the above solution (change the file path/python version based on your environment):

sed -i 's/transform_plan_raw =.*/transform_plan_raw = js/g' /usr/local/lib/python3.10/site-packages/pytube/cipher.py

If you are using Docker, add this to your Dockerfile:

RUN sed -i 's/transform_plan_raw =.*/transform_plan_raw = js/g' /usr/local/lib/python3.10/site-packages/pytube/cipher.py

@sky24h
Copy link

sky24h commented Mar 20, 2023

I just patched this error by simply modifying {home}/.local/lib/python3.7/site-packages/pytube/cipher.py Line 411

transform_plan_raw = find_object_from_startpoint(raw_code, match.span()[1] - 1)

to

transform_plan_raw = js

And everything works fine. Hope this can solve your problem.

This works fine for me!
Just for reference, if anybody faces the issue that this is not working or the code is not at line 411,
do 'pip install pytube==12.1.2' first, and then change line 411 as described.

@alvations
Copy link

alvations commented Mar 21, 2023

BTW, if anyone wants to hot-plug the fix from @dark9ive #1498 (comment)

Here's an example:

import re
import mock

from pytube.cipher import get_throttling_function_code

def patched_throttling_plan(js: str):
    """Patch throttling plan, from https://github.com/pytube/pytube/issues/1498"""
    raw_code = get_throttling_function_code(js)

    transform_start = r"try{"
    plan_regex = re.compile(transform_start)
    match = plan_regex.search(raw_code)

    #transform_plan_raw = find_object_from_startpoint(raw_code, match.span()[1] - 1)
    transform_plan_raw = js

    # Steps are either c[x](c[y]) or c[x](c[y],c[z])
    step_start = r"c\[(\d+)\]\(c\[(\d+)\](,c(\[(\d+)\]))?\)"
    step_regex = re.compile(step_start)
    matches = step_regex.findall(transform_plan_raw)
    transform_steps = []
    for match in matches:
        if match[4] != '':
            transform_steps.append((match[0],match[1],match[4]))
        else:
            transform_steps.append((match[0],match[1]))

    return transform_steps


with mock.patch('pytube.cipher.get_throttling_plan', patched_throttling_plan):
    from pytube import YouTube
    url = 'https://www.youtube.com/watch?v=ZBVrPWwSlRM'

    video = YouTube(url)
    audio = video.streams.filter(only_audio=True, file_extension='mp4')[0]
    audio.download()

@bl-cn
Copy link

bl-cn commented Mar 21, 2023

BTW, if anyone wants to hot-plug the fix from @dark9ive #1498 (comment)

Here's an example:

import re
import mock

from pytube.cipher import get_throttling_function_code

def patched_throttling_plan(js: str):
    """Patch throttling plan, from https://github.com/pytube/pytube/issues/1498"""
    raw_code = get_throttling_function_code(js)

    transform_start = r"try{"
    plan_regex = re.compile(transform_start)
    match = plan_regex.search(raw_code)

    #transform_plan_raw = find_object_from_startpoint(raw_code, match.span()[1] - 1)
    transform_plan_raw = js

    # Steps are either c[x](c[y]) or c[x](c[y],c[z])
    step_start = r"c\[(\d+)\]\(c\[(\d+)\](,c(\[(\d+)\]))?\)"
    step_regex = re.compile(step_start)
    matches = step_regex.findall(transform_plan_raw)
    transform_steps = []
    for match in matches:
        if match[4] != '':
            transform_steps.append((match[0],match[1],match[4]))
        else:
            transform_steps.append((match[0],match[1]))

    return transform_steps


with mock.patch('pytube.cipher.get_throttling_plan', patched_throttling_plan):
    from pytube import YouTube
    url = 'https://www.youtube.com/watch?v=ZBVrPWwSlRM'

    video = YouTube(url)
    audio = video.streams.filter(only_audio=True, file_extension='mp4')[0]
    audio.download()

It works for me. Solve the problem on iPad. Thanks @alvations

nishant131 added a commit to nishant131/youtube-downloader that referenced this issue Mar 21, 2023
nishant131 added a commit to nishant131/youtube-downloader that referenced this issue Mar 21, 2023
@nishant131
Copy link

nishant131 commented Mar 21, 2023

People using Docker or some CI/CD tools for installing can use a wheel file to install the updated version until this fix gets into an official release. Download this wheel file, move it to appropriate location in your project/ repo and update your requirements.txt accordingly.

To get the wheel file I cloned @JLeopolt 's forked repo and ran the following commands.

cd pytube
pip install wheel setuptools
python setup.py bdist_wheel

@Fawwad-891
Copy link

But where is cipher.py file in android?
I am making android app I need help

HamletMedina pushed a commit to HamletMedina/pytube that referenced this issue Sep 27, 2023
about [ERROR] 'NoneType' object has no attribute 'span'
@jsantamariag
Copy link

I just patched this error by simply modifying {home}/.local/lib/python3.7/site-packages/pytube/cipher.py Line 411

transform_plan_raw = find_object_from_startpoint(raw_code, match.span()[1] - 1)

to

transform_plan_raw = js

And everything works fine. Hope this can solve your problem.

This actually worked! Don't know why, i guess youtube updating it's API so often makes things stop working? Anyways thanks a lot

@Staheos
Copy link

Staheos commented Sep 27, 2023

I just patched this error by simply modifying {home}/.local/lib/python3.7/site-packages/pytube/cipher.py Line 411

transform_plan_raw = find_object_from_startpoint(raw_code, match.span()[1] - 1)

to

transform_plan_raw = js

And everything works fine. Hope this can solve your problem.

Still working today

@SEGATON
Copy link

SEGATON commented Sep 28, 2023

IT STARTED WORKING AGAIN!!!!!!!!!!!
WHAT HAPPENED? HOW WAS IT FIXED? I DIDN'T EVEN TOUCH MY CODE--IT DIDN'T WORK FOR 3 DAYS NOW IT SUDDENLY STARTED WORKING. WONDERFUL NOW I DON'T HAVE TO WASTE TIME ON YT-DLP, MY OH MY HOW ELATED I AM

@bizzome
Copy link

bizzome commented Sep 28, 2023

IT STARTED WORKING AGAIN!!!!!!!!!!! WHAT HAPPENED? HOW WAS IT FIXED? I DIDN'T EVEN TOUCH MY CODE--IT DIDN'T WORK FOR 3 DAYS NOW IT SUDDENLY STARTED WORKING. WONDERFUL NOW I DON'T HAVE TO WASTE TIME ON YT-DLP, MY OH MY HOW ELATED I AM

A branch merged today by @jhg3410 dealed with the error.

@jhg3410
Copy link

jhg3410 commented Sep 29, 2023

IT STARTED WORKING AGAIN!!!!!!!!!!! WHAT HAPPENED? HOW WAS IT FIXED? I DIDN'T EVEN TOUCH MY CODE--IT DIDN'T WORK FOR 3 DAYS NOW IT SUDDENLY STARTED WORKING. WONDERFUL NOW I DON'T HAVE TO WASTE TIME ON YT-DLP, MY OH MY HOW ELATED I AM

A branch merged today by @jhg3410 dealed with the error.

no, I just modified it in my repository and didn't touch the code on Pytube.
and even with my code before the revision, the issue has been solved for me

jhg3410 added a commit to jhg3410/Movie that referenced this issue Feb 21, 2024
@Carlolopespesia
Copy link

I just patched this error by simply modifying {home}/.local/lib/python3.7/site-packages/pytube/cipher.py Line 411

transform_plan_raw = find_object_from_startpoint(raw_code, match.span()[1] - 1)

to

transform_plan_raw = js

And everything works fine. Hope this can solve your problem.

It works! Thank 🎇

@itsromsdown
Copy link

Hi!

I'm using the latest version, and it worked well until a few days ago. but I got this error today many times while downloading some youtube videos.

I looked into this issue pages and I suspect this is a recurring issue when google changes the js file from their end. I would appreciate it if anyone could provide a solution. Thanks!

File "/usr/local/lib/python3.8/dist-packages/pytube/cipher.py", line 360, in get_throttling_plan', ' raw_code = get_throttling_function_code(js)', ' File "/usr/local/lib/python3.8/dist-packages/pytube/cipher.py", line 277, in get_throttling_function_code', " code_lines_list = find_object_from_startpoint(js, match.span()[1]).split('\n')", "AttributeError: 'NoneType' object has no attribute 'span'"]

you are my hero thank you so much

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