Bambu Lab X1 X1C MQTT

image

Success! Moving the subscribe to the topic into the on_connect method looks like it fixed a race condition.

1 Like

Got most of the existing sensors in @greghesp’s integration working.

Need to work out what’s up with the fans. Chamber and target temperatures never get set as the P1P doesn’t publish those (probably doesn’t even have a chamber temperature sensor?).

Update: Fans was a dumb bug on my part. Have current stage working now too although it and speed don’t initialize until they change and the P1P sends out an update for them.

2 Likes

Yeah, I feel like for the P1P most of the sensors should be marked as unavailable until an update comes for them, or they get a default value of like 0 or something.

Also, is that cooling fan trying to cool the sun :laughing:

Would be nice for the P1P work you do to put it into a pull request. It’s probably best practice to treat all sensors as “unavailable until we get an update” regardless of printer, and just for the P1P there are some sensors we never even make probably.

I’m trying to set this up so I can trigger prints I manually send to the printers via FTP but the nodered plugin is broken for HA :frowning:
Is there a way to run nodered externally then connect to HA or am I stuck until it gets fixed?

Do you mean the NodeRed Addon if you’re using HassOS? NodeRed can be run externally for sure, easiest would be in a docker container. I myself run Home-Assistant-Core instead of HassOS so I am forced to have NodeRed, MQTT, EspHome etc all externally.

Also FYI - the nodered flow doesn’t have anything to send and start prints, though now that I think about it, it seems like it would be possible, just tedious to use with HA. Pretty simple to get a node in NR to list the files from the printer FTP, and I know way earlier in the thread there is the command to start a print from a file + task name, so it is possible.

Yep, I plan to work out a good way to hide the sensors that don’t exist (or aren’t published) on the P1P. I’m just happy to get things working :slight_smile:. Trying to decide if the code should try and auto-detect X1 vs P1P and just do the right thing or require an explicit choice given that the P1P requires the serial number to be provided by the user. I’m leaning towards the explicit choice so that the extra serial number requirement can be skipped by X1 owners.

The fans were just a slip as I simplified some code and instead of it being the intended ‘new raw value or previous raw value if the value isn’t in this specific payload’ converted into a percentage it became previous percentage converted (multiplied) to a percentage again. So all the payloads coming through without fan values cause the number to exponentially increase.

Once I’ve got it tidied up and I have confirmed (as best I can without one) that I haven’t broken any X1 scenarios with my changes, I’ll do a pull request for review.

1 Like

Is there a good way of having a sensor report N/A as well as a numerical value (not as the same time)? Both for cases where someone tries to query a sensor the P1P simply doesn’t have/publish or for cases where it has decided to stop publishing. I see, for instance, that now the printer has completely cooled down it’s still publishing bed temperature somewhat regularly but has stopped publishing nozzle temperature so after restarting home assistant that’s just sat at the default of 0C that I set it to. I’d like to start it at something like ‘N/A’ and maybe time it out back to N/A if it hasn’t been seen for a while.

More sensors are working than I thought. Target temperatures are being set. Maybe that’s only done during the first pre-print phase since they didn’t seem to be being pushed mid-print:

Not sure what’s up with that 5C chamber temperature. It’s definitely toastier than that in my house and even toastier still inside the printer enclosure!

I’ve been slowly working on some of that. My constant hangup is file uploads. I haven’t found “friendly” solution as of yet. If anybody has a great idea as how to upload a file through HA (that’ll wind up in a NR HTTP In node), I’m all ears.

1 Like

Yeah, yesterday I was thinking “I could probably list current prints on the printer in a dropdown, but then how does HA UI allow me to then use that selection in a print now button…”. For uploading, that’s an entirely different beast. Almost feel like the only good solution would be to make a panel be an embedded FTP Client GUI served over a webpage, but that also seems annoying :laughing:

The NR flow already has an issue with the file upload stuff when it’s using my FTP image/3mf fetcher. I had a good 5 second delay after downloading the file to unzip but if it were a large file, it errors due to time. Changed my delay to like 30s to be safe. Tried file watching, but it triggers every time a chunk downloads so not too useful until messages “stop”. I couldn’t imagine the reverse with uploading, not knowing if it’s all done yet and recognized by the printer.

Made a small update to the NodeRed flow (rev 17) that should be helpful to those who want to setup automations through HomeAssistant rather than NodeRed.

Added two device-automation triggers to the printer for when the Lidar is in use, and then when it is not in use. It essentially just parses the Stage for if it contains “lidar” or not, but offers it as a native Trigger for HA Automations.

Saw some Bambu studio checkins on GitHub that were starting to add lan mode support for the P1P as of a specific mc software version. Presumably that will be the one that enables ftp to the device.

Do someone of you have experiance with mqtts / TLS / SSL / Certificate login?
Something will change in “near future” and it would be nice to be prepared :wink:

If it’s a simple username and password login over a secured port, then it should be fine, but if it gets a bit more complex well, that would be something.

I wouldn’t be surprised if things changed to be honest. I just hope that if it gets locked down to credentials, we have a way to obtain them (similarly to how we can connect to the FTP by using a standard username and the unique, regeneratable lan-only access password).

Think on the next firmware update I may hold off for a few days just in case… or really any in general. I was already planning to so I could see how it detects new firmware version and maybe let there be a notification in HA about it, and possibly even trigger the update but that would take at least two firmware update cycles to “get right” I think.

@WolfwithSword I have sent you an private message.

If I understood correctly, you didn’t use node red, but used the mqtt bridge directly, then added sensors to (I’m guessing) configuration.yaml under mqtt: sensors: If that’s the case, would you mind sharing your sensor configs please?

This was the missing “link” for me. If I use now SSL enctryption and the ftp username and password I am able to connect again. So no big change needed for upcomming FW versions :wink:

@MJWMJW I use also Node-Red (if you question goes in my direction)

1 Like

I was aiming @darkorb

At the top of the post is a little reply button. If you press that it shows you what the post was a reply to. At least that’s how I figure it out, there may be a better way. Probably should have put at @ in as well.

1 Like

I see this in the MQTT data pushed by my P1P:

"upgrade_state":{"sequence_id":0,"progress":"","status":"","consistency_request":false,"dis_state":0,"err_code":0,"force_upgrade":false,"message":"","module":"","new_version_state":2,"new_ver_list":[]}

as part of a big initial state dump message (23 lines in the console vs only 2 for most messages). Not sure what generated it since I haven’t seen it much - possibly only triggered by starting a print as I have 4 of them in my log where I started 2 prints (immediately canceled the first as I realized I probably didn’t have enough filament to complete it in one go and didn’t want to get a filament swap zit). It was a huge dump of state - full ams state in there and light state. If there were a way to trigger that on demand it would make initial state setup in the integration a lot easier. Looks like it is associated with the start of printing since it has the gcode filename in there.

‘drying_temp’ - intriguing entry I see in the ams section. I wonder if they originally planned it to be heated?

{
  "print": {
    "bed_target_temper": 0,
    "bed_temper": 22.9375,
    "nozzle_temper": 34.8125,
    "nozzle_target_temper": 0,
    "chamber_temper": 5,
    "big_fan1_speed": "0",
    "big_fan2_speed": "0",
    "cooling_fan_speed": "0",
    "heatbreak_fan_speed": "0",
    "gcode_state": "IDLE",
    "mc_print_error_code": "0",
    "mc_print_line_number": "0",
    "mc_print_stage": "1",
    "mc_percent": 0,
    "mc_print_sub_stage": 0,
    "mc_remaining_time": 0,
    "task_id": "0",
    "wifi_signal": "-60dBm",
    "project_id": "0",
    "profile_id": "0",
    "subtask_id": "0",
    "subtask_name": "",
    "lifecycle": "product",
    "sdcard": true,
    "print_error": 0,
    "hw_switch_state": 1,
    "gcode_file_prepare_percent": "0",
    "home_flag": 0,
    "ams_status": 0,
    "gcode_file": "",
    "ams_rfid_status": 6,
    "spd_mag": 100,
    "spd_lvl": 2,
    "force_upgrade": false,
    "mess_production_state": "active",
    "print_type": "idle",
    "hms": [],
    "online": {
      "ahb": false,
      "rfid": false,
      "version": 1281103920
    },
    "ams": {
      "ams": [
        {
          "id": "0",
          "humidity": "3",
          "temp": "0.0",
          "tray": [
            {
              "id": "0",
              "remain": -1,
              "k": 0.019999999552965164,
              "n": 1.399999976158142,
              "tag_uid": "0000000000000000",
              "tray_id_name": "",
              "tray_info_idx": "GFL99",
              "tray_type": "PLA",
              "tray_sub_brands": "",
              "tray_color": "808040FF",
              "tray_weight": "0",
              "tray_diameter": "0.00",
              "drying_temp": "0",
              "drying_time": "0",
              "bed_temp_type": "0",
              "bed_temp": "0",
              "nozzle_temp_max": "240",
              "nozzle_temp_min": "190",
              "xcam_info": "000000000000000000000000",
              "tray_uuid": "00000000000000000000000000000000"
            },
            {
              "id": "1",
              "remain": -1,
              "k": 0.019999999552965164,
              "n": 1.399999976158142,
              "tag_uid": "0000000000000000",
              "tray_id_name": "",
              "tray_info_idx": "GFL99",
              "tray_type": "PLA",
              "tray_sub_brands": "",
              "tray_color": "000000FF",
              "tray_weight": "0",
              "tray_diameter": "0.00",
              "drying_temp": "0",
              "drying_time": "0",
              "bed_temp_type": "0",
              "bed_temp": "0",
              "nozzle_temp_max": "250",
              "nozzle_temp_min": "190",
              "xcam_info": "000000000000000000000000",
              "tray_uuid": "00000000000000000000000000000000"
            },
            {
              "id": "2",
              "remain": -1,
              "k": 0.029999999329447746,
              "n": 1.399999976158142,
              "tag_uid": "0000000000000000",
              "tray_id_name": "",
              "tray_info_idx": "GFL99",
              "tray_type": "PLA",
              "tray_sub_brands": "",
              "tray_color": "FF8000FF",
              "tray_weight": "0",
              "tray_diameter": "0.00",
              "drying_temp": "0",
              "drying_time": "0",
              "bed_temp_type": "0",
              "bed_temp": "0",
              "nozzle_temp_max": "240",
              "nozzle_temp_min": "190",
              "xcam_info": "000000000000000000000000",
              "tray_uuid": "00000000000000000000000000000000"
            },
            {
              "id": "3",
              "remain": -1,
              "k": 0.019999999552965164,
              "n": 1.399999976158142,
              "tag_uid": "0000000000000000",
              "tray_id_name": "",
              "tray_info_idx": "GFS00",
              "tray_type": "PLA-S",
              "tray_sub_brands": "",
              "tray_color": "C0C0C0FF",
              "tray_weight": "0",
              "tray_diameter": "0.00",
              "drying_temp": "0",
              "drying_time": "0",
              "bed_temp_type": "0",
              "bed_temp": "0",
              "nozzle_temp_max": "240",
              "nozzle_temp_min": "190",
              "xcam_info": "000000000000000000000000",
              "tray_uuid": "00000000000000000000000000000000"
            }
          ]
        }
      ],
      "ams_exist_bits": "1",
      "tray_exist_bits": "f",
      "tray_is_bbl_bits": "f",
      "tray_now": "255",
      "tray_read_done_bits": "f",
      "tray_reading_bits": "0",
      "tray_tar": "255",
      "version": 3,
      "insert_flag": true,
      "power_on_flag": false
    },
    "ipcam": {
      "ipcam_dev": "1",
      "ipcam_record": "enable"
    },
    "vt_tray": {
      "id": "254",
      "k": 0.019999999552965164,
      "n": 1.399999976158142
    },
    "lights_report": [
      {
        "node": "chamber_light",
        "mode": "off"
      }
    ],
    "upgrade_state": {
      "sequence_id": 0,
      "progress": "",
      "status": "",
      "consistency_request": false,
      "dis_state": 0,
      "err_code": 0,
      "force_upgrade": false,
      "message": "",
      "module": "",
      "new_version_state": 2,
      "new_ver_list": []
    },
    "command": "push_status",
    "msg": 0,
    "sequence_id": "31"
  }
}

And this answers where the mysterious chamber temp of 5C was coming from - “chamber_temper”:5. Not a bug, just what the P1P told me.

Taking a look at the P1P full statement there, there’s some more strange changes. For example, spd_lvl is 254 for the mag of 100. I forget but does the P1P only have a single standard speed? In that case would be better to just use speed % instead of a speed name for the P1P, and then not give the option to change speed via name.

Also I don’t recognize that “print_type” key, so either it’s P1P unique or it’s coming in a future update along with some other new sensors perhaps.

I believe the drying temp and time are included on bambu spools to help detect if drying of a filament is needed given the overall AMS humidity level / temperature. Technically the AMS works as a drybox but not a dryer, but it is kind of nice to have that data available.

I also don’t recognize “vt_tray”. I wonder if that’s for a virtual tray, aka a non AMS spool. Would love if this were configurable via the slicer and could get data for it, but I doubt it, probably a placeholder for now - given there’s a K and N value which I also don’t recognize for the AMS trays. Wonder what they represent.

Weird. I see this in the original one I posted:
“spd_mag”:100,“spd_lvl”:254
but a fresh one I grabbed this morning and happened to prettify (now above) has:
“spd_mag”: 100,
“spd_lvl”: 2,
As far as I can tell the way the P1P exposes speeds (and it’s the same options as the X1), is the same as the initial code in the integration just worked. So I’m not sure what’s up with the 254 value.

Logs have:
“print_type”: “idle”,
“print_type”: “cloud”,
I’m guessing other options might be lan or sdcard.

The K value is the configured value in the slicer. So most of mine are the default of 0.020 but my tray 3 has the single filament I’ve calibrated K for so far at 0.030. It’s odd the values have become very slightly less than the values I inputted though. No idea what N is.

Yes, a virtual tray would be nice to get occasional 5 color prints going (where the 5th color is rarely switched to!).