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

Inconsistency in Python import #3481

Open
MangelMaxime opened this issue Jun 27, 2023 · 2 comments
Open

Inconsistency in Python import #3481

MangelMaxime opened this issue Jun 27, 2023 · 2 comments
Labels
python Python

Comments

@MangelMaxime
Copy link
Member

MangelMaxime commented Jun 27, 2023

Hello @dbrattli,

I am writing the documentation for Python on Fable website and found some strange behaviour.

I don't know if they are bugs or expected, as I am not a python expert.

I have a hello.py file with this content:

def say_hello():
    print("Hello world")

[<Import("say_hello", "./hello.py")>]
let say_hello : unit -> unit = jsNative

say_hello()

Generates

from hello import say_hello

say_hello()

So it means that it is stripping the ./ and .py from the path. However, using a relative path for * doesn't strip anything

[<Import("*", "./hello.py")>]
let say_hello : unit -> unit = jsNative

say_hello()

generates

import ./hello.py as say_hello

say_hello()

The same kind of problem occurs when trying to use:

  • [<ImportAll("./hello.py")>]
  • [<ImportDefault("./hello.py")>]

[<Import("*", "hello")>]
let say_hello : unit -> unit = jsNative

say_hello()

generates

import hello

hello()

This generates an error at runtime TypeError: 'module' object is not callable

I would have expected the generated code to be

from hello import *

say_hello()

[<ImportAll("hello")>]
let say_hello : unit -> unit = jsNative

generates

import hello

hello()

Should it be ?

from hello import *

say_hello()

[<ImportAll("./hello.py")>]
let say_hello : unit -> unit = jsNative

generates

import ./hello.py as hello

hello()

Should it strip the path?

Also, generated code doesn't work because it tries to execute the module instead of hello.say_hello()


[<ImportDefault("./hello.py")>]
let say_hello : unit -> unit = jsNative

say_hello()

generates

from hello import hello

hello()

The code will fail at runtime, but I don't know what is the expected output here.

but

[<ImportDefault("hello")>]
let say_hello : unit -> unit = jsNative

say_hello()

generates

import hello

hello()

Is it normal to have a difference here? And the code will fails to, but I don't know what is the expected output here.

Related information

  • Fable version: 4.1.4
  • Operating system
@MangelMaxime
Copy link
Member Author

MangelMaxime commented Jun 27, 2023

let hi : unit -> unit = import "*" "./hello.py"

hi()

generates

from typing import Callable
import ./hello.py as hello

hi: Callable[[], None] = hello

hi()

which is an invalid code.


let say_hello : unit -> unit = importAll "hello"

say_hello()

generates

import hello
from typing import Callable

say_hello: Callable[[], None] = hello

say_hello()

I think it should generates

from hello import * 
from typing import Callable

say_hello()

or

from hello import * 
from typing import Callable

say_hello_1: Callable[[], None] = say_hello

say_hello_1()

if we need the variable assignement.

@joprice
Copy link
Contributor

joprice commented Dec 2, 2024

There's also an issue with importSideEffects, which generates from X import without any identifier following the import statement, which is invalid syntax.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
python Python
Projects
None yet
Development

No branches or pull requests

2 participants