nerdblood

joined 1 year ago
[–] nerdblood@programming.dev 1 points 10 months ago

Sqlbolt has been good so far, just started myself

 

I'm slowly starting Rust for Rustaceans, and it's already poking holes in my understanding of Rust. Here's a couple initial questions I have:

A shared reference, &T is , as the name implies, a pointer that may be shared. Any number of references may exist to the same value, and each shared reference is Copy, so you can trivially make more of them

I don't understand why a shared reference has to implement copy. In fact, isn't this not true just by the fact that references work for Strings and Strings size can't be known at compile time?

  1. I'm having trouble with the idea of assigning a new value to a mutable reference.

let mut x = Box::new(42); *x = 84;

Why in this example, is the assignment dereferenced. Why not just do x=84? is it dereferenced specifically because is Boxed on the heap?

[–] nerdblood@programming.dev 1 points 1 year ago

Indeed it does haha, thanks

[–] nerdblood@programming.dev 1 points 1 year ago (2 children)

I'm new to multithreaded programming. How would some other thread create it? Like what's the real-world scenario?

[–] nerdblood@programming.dev 1 points 1 year ago

I think I had that in a few attempts, I can't remember why I removed it. Thanks for pointing this out.

[–] nerdblood@programming.dev 1 points 1 year ago (10 children)

I managed to get this working, but there has to be a better way. How else could I write this?

  pub async fn insert_or_return_user(
        db: &DbConn,
        partial_user: Auth0UserPart,
    ) -> Result {
        let user = users::ActiveModel {
            email: Set(partial_user.email.to_owned()),
            email_verified: Set(partial_user.email_verified.to_owned()),
            auth0_sub: Set(partial_user.sub.to_owned()),
            ..Default::default()
        };

        let result = user.clone().insert(db).await;

        match result {
            Ok(u) => {
                println!("{u:#?}");
                Ok(u.try_into_model().unwrap() as UsersModel)
            }
            Err(error) => {
                let user = Users::find()
                    .filter(users::Column::Auth0Sub.eq(&partial_user.sub))
                    .one(db)
                    .await?;

                Ok(user.unwrap() as UsersModel)
            }
        }
    }
 

in sequelize (javascript) it's pretty straightforward to either find a record, or create it if it doesn't exist. I don't see anything similar with sea-orm. There's a 'save' method that seems to insert or update, but I need to know details about the record ahead of time :/

Any ideas?

https://sequelize.org/docs/v6/core-concepts/model-querying-finders/

[–] nerdblood@programming.dev 3 points 1 year ago

🤣

We're a pretty darn good minor league baseball team if you ask me

[–] nerdblood@programming.dev 2 points 1 year ago

It should be wrapped in an array, not an object. Then it's valid. The problem was that I was trying to use an enum.

 

The first post had a couple errors that made things confusing. I have an accurately formatted JSON response, but I still can't seem to deserialize it.

I keep getting an error where the response isn’t matching up as expected: Error("data did not match any variant of untagged enum NationResponse"

I have a JSON response that looks like this:

 {
      {
            "id": 1,
            "country": "usa"
        },
        [
            {
                "id": 1,
                "age": 37,
                "name": "John"
            },
            {
                "id": 2,
                "age": 21,
                "name": "Nick"
            },
        ]
}

And I’m trying to deserialize it, but I can’t seem to get it right. Isn’t this accurate?

#[derive(Deserialize, Debug)]
#[serde(untagged)]
enum NationResponse {
    Nation(Nation),
    People(Vec),
}

struct Person {
    id : i32,
    age : i32,
    name : String
}

struct Nation {
    id : i32,
    country : String
}

Edit:

The problem I was actually experiencing was trying to use an enum as the response. Yes the formatting for my example was wrong (it should have been an array). But the structure besides that was accurate.

What I needed was Vec>

[–] nerdblood@programming.dev 1 points 1 year ago

Yes, that's what I meant, but no I can't edit it :/

[–] nerdblood@programming.dev 2 points 1 year ago* (last edited 1 year ago)

I got the response wrong, here's what I'm using that isn't working:

enum NationResponse {
    Nation(Nation),
    People(Vec),
}

Why the heck can't I edit the original post after a comment is made?

[–] nerdblood@programming.dev 4 points 1 year ago (1 children)

Oh man, I didn't know debug_handler existed. Sure enough I had a missing derived attribute... not sure how but Serde serialize and deserialize were missing, so when I was trying to return Ok(Json(army)) it was failing. Thanks so much!

[–] nerdblood@programming.dev 1 points 1 year ago

Thanks for the reply! I don't know what you mean by extensions, but the state is literally just the DB connection:

struct AppState { conn: DatabaseConnection, }

 

Not sure what happened exactly... it was working fine and I didn't change anything in this file. It has to be related to something I did recently:

  1. Ran a migration adding a unique constraint on a table
  2. Generated two new entities of a couple very basic tables.

The handler I'm using isn't even using the new tables, so I don't know why this randomly broke. Anyone have any ideas? Or even some guidance on how to decipher that obscure error would be helpful.

[–] nerdblood@programming.dev 1 points 1 year ago

Nice, thanks... looking into these now.

 

I've been trying to use OneCell, but I keep having errors trying to set it up to handle a mutable vector that I can push to.

I know there's going to be some answers telling me maybe not to use a singleton, but the alternative of passing a vector all around throughout my code is not ergonmic at all.

I've tried lots of things, but this is where I'm at right now. Specifically I'm just having trouble initializing it.

`/**

  • LOG_CELL
  • Stores a vec of Strings that is added to throughout the algorithm with information to report
  • To the end user and developer */ pub static LOG_CELL: OnceLock<&mut Vec> = OnceLock::new();

pub fn set_log() { LOG_CELL.set(Vec::new()); }

pub fn push_log(message: String) { if let Some(vec_of_messages) = LOG_CELL.get() { let something = *vec_of_messages; something.push(message); } } `

 

I've mostly been putting functions, structs enums and tests in the same file and it's starting to feel like a mess... I am constantly losing track of which function is where and I'm never quite sure if I have code in the right place. I know this is kind of vague, but that's been my general feeling while working in my largest personal project so far. It's essentially a large Algorithm that has many smaller steps that needs to run in a sequence.

I think I might just have too many loose functions and maybe I should use more impl methods and traits? I'm also thinking I should try the builder pattern in a few spots.

Anyone have any guidance on code organization in rust?

 

I know there's mockall which seems to be geared towards implementation methods and traits, but I'm wondering about just structs with non-function properties.

In my tests, I want to define initialized structs with values. It works fine to just do it like I normally would in code, but I'm wondering if there's more to it than that. Like if I have a cat struct:

struct Cat { name : String } `

#[cfg(test)] pub mod test { use super::Cat; fn test_create_cat() -> Cat { Cat { name. : String::from("Fred") }; }

That's fine, but should I be doing it differently? What about mockall, is it not meant for structs with properties?

 

for example, I have a file structure that looks like this:

action/
   attack.rs
   attack.test.rs
   mod.rs

But this doesn't work in the mod file:

pub mod attack.test;

and neither does:

pub mod "attack.test";

 

I'm wondering with my game project how best to handle types. I'm basically fetching all the rows in a particular table and creating a struct to represent that data. I then have like 5 or 6 sequential steps I'm trying to go through where I need to modify those initial values from the db.

My first thought was to have a base type called 'BaseArmy', then I needed to add new temporary properties that are not in the db and not represented in the original struct, so I decided to create a new struct 'Army'. The problem is I keep running into errors when passing converting from BaseArmy to Army. I tried writing a From impl, but it wasn't working (and I'm not even sure if it's the approach I should be taking).

So should I:

  1. Have multiple different types to handle these kinds of cases
  2. Have just one type somehow where I add properties to it? If so, how? I recently tried using Options for the fields that are not initially available, and that seems to be working but it feels weird.
 

My program is small enough that in TS/JS I'd normally just store the data in some global variable to be access from whatever elsewhere in the app. But with Rust from what I can tell this doesn't seem to be a common practice. How should i handle this?

More specifically, I need to:

  1. program start, fetch data from my db (DONE)
  2. store this data somehow somewhere
  3. access said data (for read only in this use case)

Thanks for any insights here!

 

I've been learning rust for a while now and a key tactic that's helped me along has been asking questions on reddit, often very specific to code I'm writing. I'll usually attempt a solution on my own until I'm sufficiently stuck then ask for help.

Can I post those questions here or is there a better community for it?

view more: next ›