mirror of
				https://github.com/iv-org/invidious.git
				synced 2025-10-31 12:42:09 +00:00 
			
		
		
		
	Move user preferences structure to a separate file
This commit is contained in:
		
							
								
								
									
										257
									
								
								src/invidious/user/preferences.cr
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										257
									
								
								src/invidious/user/preferences.cr
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,257 @@ | ||||
| struct Preferences | ||||
|   include JSON::Serializable | ||||
|   include YAML::Serializable | ||||
|  | ||||
|   property annotations : Bool = CONFIG.default_user_preferences.annotations | ||||
|   property annotations_subscribed : Bool = CONFIG.default_user_preferences.annotations_subscribed | ||||
|   property autoplay : Bool = CONFIG.default_user_preferences.autoplay | ||||
|   property automatic_instance_redirect : Bool = CONFIG.default_user_preferences.automatic_instance_redirect | ||||
|  | ||||
|   @[JSON::Field(converter: Preferences::StringToArray)] | ||||
|   @[YAML::Field(converter: Preferences::StringToArray)] | ||||
|   property captions : Array(String) = CONFIG.default_user_preferences.captions | ||||
|  | ||||
|   @[JSON::Field(converter: Preferences::StringToArray)] | ||||
|   @[YAML::Field(converter: Preferences::StringToArray)] | ||||
|   property comments : Array(String) = CONFIG.default_user_preferences.comments | ||||
|   property continue : Bool = CONFIG.default_user_preferences.continue | ||||
|   property continue_autoplay : Bool = CONFIG.default_user_preferences.continue_autoplay | ||||
|  | ||||
|   @[JSON::Field(converter: Preferences::BoolToString)] | ||||
|   @[YAML::Field(converter: Preferences::BoolToString)] | ||||
|   property dark_mode : String = CONFIG.default_user_preferences.dark_mode | ||||
|   property latest_only : Bool = CONFIG.default_user_preferences.latest_only | ||||
|   property listen : Bool = CONFIG.default_user_preferences.listen | ||||
|   property local : Bool = CONFIG.default_user_preferences.local | ||||
|   property vr_mode : Bool = CONFIG.default_user_preferences.vr_mode | ||||
|   property show_nick : Bool = CONFIG.default_user_preferences.show_nick | ||||
|  | ||||
|   @[JSON::Field(converter: Preferences::ProcessString)] | ||||
|   property locale : String = CONFIG.default_user_preferences.locale | ||||
|  | ||||
|   @[JSON::Field(converter: Preferences::ClampInt)] | ||||
|   property max_results : Int32 = CONFIG.default_user_preferences.max_results | ||||
|   property notifications_only : Bool = CONFIG.default_user_preferences.notifications_only | ||||
|  | ||||
|   @[JSON::Field(converter: Preferences::ProcessString)] | ||||
|   property player_style : String = CONFIG.default_user_preferences.player_style | ||||
|  | ||||
|   @[JSON::Field(converter: Preferences::ProcessString)] | ||||
|   property quality : String = CONFIG.default_user_preferences.quality | ||||
|   @[JSON::Field(converter: Preferences::ProcessString)] | ||||
|   property quality_dash : String = CONFIG.default_user_preferences.quality_dash | ||||
|   property default_home : String? = CONFIG.default_user_preferences.default_home | ||||
|   property feed_menu : Array(String) = CONFIG.default_user_preferences.feed_menu | ||||
|   property related_videos : Bool = CONFIG.default_user_preferences.related_videos | ||||
|  | ||||
|   @[JSON::Field(converter: Preferences::ProcessString)] | ||||
|   property sort : String = CONFIG.default_user_preferences.sort | ||||
|   property speed : Float32 = CONFIG.default_user_preferences.speed | ||||
|   property thin_mode : Bool = CONFIG.default_user_preferences.thin_mode | ||||
|   property unseen_only : Bool = CONFIG.default_user_preferences.unseen_only | ||||
|   property video_loop : Bool = CONFIG.default_user_preferences.video_loop | ||||
|   property extend_desc : Bool = CONFIG.default_user_preferences.extend_desc | ||||
|   property volume : Int32 = CONFIG.default_user_preferences.volume | ||||
|  | ||||
|   module BoolToString | ||||
|     def self.to_json(value : String, json : JSON::Builder) | ||||
|       json.string value | ||||
|     end | ||||
|  | ||||
|     def self.from_json(value : JSON::PullParser) : String | ||||
|       begin | ||||
|         result = value.read_string | ||||
|  | ||||
|         if result.empty? | ||||
|           CONFIG.default_user_preferences.dark_mode | ||||
|         else | ||||
|           result | ||||
|         end | ||||
|       rescue ex | ||||
|         if value.read_bool | ||||
|           "dark" | ||||
|         else | ||||
|           "light" | ||||
|         end | ||||
|       end | ||||
|     end | ||||
|  | ||||
|     def self.to_yaml(value : String, yaml : YAML::Nodes::Builder) | ||||
|       yaml.scalar value | ||||
|     end | ||||
|  | ||||
|     def self.from_yaml(ctx : YAML::ParseContext, node : YAML::Nodes::Node) : String | ||||
|       unless node.is_a?(YAML::Nodes::Scalar) | ||||
|         node.raise "Expected scalar, not #{node.class}" | ||||
|       end | ||||
|  | ||||
|       case node.value | ||||
|       when "true" | ||||
|         "dark" | ||||
|       when "false" | ||||
|         "light" | ||||
|       when "" | ||||
|         CONFIG.default_user_preferences.dark_mode | ||||
|       else | ||||
|         node.value | ||||
|       end | ||||
|     end | ||||
|   end | ||||
|  | ||||
|   module ClampInt | ||||
|     def self.to_json(value : Int32, json : JSON::Builder) | ||||
|       json.number value | ||||
|     end | ||||
|  | ||||
|     def self.from_json(value : JSON::PullParser) : Int32 | ||||
|       value.read_int.clamp(0, MAX_ITEMS_PER_PAGE).to_i32 | ||||
|     end | ||||
|  | ||||
|     def self.to_yaml(value : Int32, yaml : YAML::Nodes::Builder) | ||||
|       yaml.scalar value | ||||
|     end | ||||
|  | ||||
|     def self.from_yaml(ctx : YAML::ParseContext, node : YAML::Nodes::Node) : Int32 | ||||
|       node.value.clamp(0, MAX_ITEMS_PER_PAGE) | ||||
|     end | ||||
|   end | ||||
|  | ||||
|   module FamilyConverter | ||||
|     def self.to_yaml(value : Socket::Family, yaml : YAML::Nodes::Builder) | ||||
|       case value | ||||
|       when Socket::Family::UNSPEC | ||||
|         yaml.scalar nil | ||||
|       when Socket::Family::INET | ||||
|         yaml.scalar "ipv4" | ||||
|       when Socket::Family::INET6 | ||||
|         yaml.scalar "ipv6" | ||||
|       when Socket::Family::UNIX | ||||
|         raise "Invalid socket family #{value}" | ||||
|       end | ||||
|     end | ||||
|  | ||||
|     def self.from_yaml(ctx : YAML::ParseContext, node : YAML::Nodes::Node) : Socket::Family | ||||
|       if node.is_a?(YAML::Nodes::Scalar) | ||||
|         case node.value.downcase | ||||
|         when "ipv4" | ||||
|           Socket::Family::INET | ||||
|         when "ipv6" | ||||
|           Socket::Family::INET6 | ||||
|         else | ||||
|           Socket::Family::UNSPEC | ||||
|         end | ||||
|       else | ||||
|         node.raise "Expected scalar, not #{node.class}" | ||||
|       end | ||||
|     end | ||||
|   end | ||||
|  | ||||
|   module URIConverter | ||||
|     def self.to_yaml(value : URI, yaml : YAML::Nodes::Builder) | ||||
|       yaml.scalar value.normalize! | ||||
|     end | ||||
|  | ||||
|     def self.from_yaml(ctx : YAML::ParseContext, node : YAML::Nodes::Node) : URI | ||||
|       if node.is_a?(YAML::Nodes::Scalar) | ||||
|         URI.parse node.value | ||||
|       else | ||||
|         node.raise "Expected scalar, not #{node.class}" | ||||
|       end | ||||
|     end | ||||
|   end | ||||
|  | ||||
|   module ProcessString | ||||
|     def self.to_json(value : String, json : JSON::Builder) | ||||
|       json.string value | ||||
|     end | ||||
|  | ||||
|     def self.from_json(value : JSON::PullParser) : String | ||||
|       HTML.escape(value.read_string[0, 100]) | ||||
|     end | ||||
|  | ||||
|     def self.to_yaml(value : String, yaml : YAML::Nodes::Builder) | ||||
|       yaml.scalar value | ||||
|     end | ||||
|  | ||||
|     def self.from_yaml(ctx : YAML::ParseContext, node : YAML::Nodes::Node) : String | ||||
|       HTML.escape(node.value[0, 100]) | ||||
|     end | ||||
|   end | ||||
|  | ||||
|   module StringToArray | ||||
|     def self.to_json(value : Array(String), json : JSON::Builder) | ||||
|       json.array do | ||||
|         value.each do |element| | ||||
|           json.string element | ||||
|         end | ||||
|       end | ||||
|     end | ||||
|  | ||||
|     def self.from_json(value : JSON::PullParser) : Array(String) | ||||
|       begin | ||||
|         result = [] of String | ||||
|         value.read_array do | ||||
|           result << HTML.escape(value.read_string[0, 100]) | ||||
|         end | ||||
|       rescue ex | ||||
|         result = [HTML.escape(value.read_string[0, 100]), ""] | ||||
|       end | ||||
|  | ||||
|       result | ||||
|     end | ||||
|  | ||||
|     def self.to_yaml(value : Array(String), yaml : YAML::Nodes::Builder) | ||||
|       yaml.sequence do | ||||
|         value.each do |element| | ||||
|           yaml.scalar element | ||||
|         end | ||||
|       end | ||||
|     end | ||||
|  | ||||
|     def self.from_yaml(ctx : YAML::ParseContext, node : YAML::Nodes::Node) : Array(String) | ||||
|       begin | ||||
|         unless node.is_a?(YAML::Nodes::Sequence) | ||||
|           node.raise "Expected sequence, not #{node.class}" | ||||
|         end | ||||
|  | ||||
|         result = [] of String | ||||
|         node.nodes.each do |item| | ||||
|           unless item.is_a?(YAML::Nodes::Scalar) | ||||
|             node.raise "Expected scalar, not #{item.class}" | ||||
|           end | ||||
|  | ||||
|           result << HTML.escape(item.value[0, 100]) | ||||
|         end | ||||
|       rescue ex | ||||
|         if node.is_a?(YAML::Nodes::Scalar) | ||||
|           result = [HTML.escape(node.value[0, 100]), ""] | ||||
|         else | ||||
|           result = ["", ""] | ||||
|         end | ||||
|       end | ||||
|  | ||||
|       result | ||||
|     end | ||||
|   end | ||||
|  | ||||
|   module StringToCookies | ||||
|     def self.to_yaml(value : HTTP::Cookies, yaml : YAML::Nodes::Builder) | ||||
|       (value.map { |c| "#{c.name}=#{c.value}" }).join("; ").to_yaml(yaml) | ||||
|     end | ||||
|  | ||||
|     def self.from_yaml(ctx : YAML::ParseContext, node : YAML::Nodes::Node) : HTTP::Cookies | ||||
|       unless node.is_a?(YAML::Nodes::Scalar) | ||||
|         node.raise "Expected scalar, not #{node.class}" | ||||
|       end | ||||
|  | ||||
|       cookies = HTTP::Cookies.new | ||||
|       node.value.split(";").each do |cookie| | ||||
|         next if cookie.strip.empty? | ||||
|         name, value = cookie.split("=", 2) | ||||
|         cookies << HTTP::Cookie.new(name.strip, value.strip) | ||||
|       end | ||||
|  | ||||
|       cookies | ||||
|     end | ||||
|   end | ||||
| end | ||||
| @@ -29,264 +29,6 @@ struct User | ||||
|   end | ||||
| end | ||||
|  | ||||
| struct Preferences | ||||
|   include JSON::Serializable | ||||
|   include YAML::Serializable | ||||
|  | ||||
|   property annotations : Bool = CONFIG.default_user_preferences.annotations | ||||
|   property annotations_subscribed : Bool = CONFIG.default_user_preferences.annotations_subscribed | ||||
|   property autoplay : Bool = CONFIG.default_user_preferences.autoplay | ||||
|   property automatic_instance_redirect : Bool = CONFIG.default_user_preferences.automatic_instance_redirect | ||||
|  | ||||
|   @[JSON::Field(converter: Preferences::StringToArray)] | ||||
|   @[YAML::Field(converter: Preferences::StringToArray)] | ||||
|   property captions : Array(String) = CONFIG.default_user_preferences.captions | ||||
|  | ||||
|   @[JSON::Field(converter: Preferences::StringToArray)] | ||||
|   @[YAML::Field(converter: Preferences::StringToArray)] | ||||
|   property comments : Array(String) = CONFIG.default_user_preferences.comments | ||||
|   property continue : Bool = CONFIG.default_user_preferences.continue | ||||
|   property continue_autoplay : Bool = CONFIG.default_user_preferences.continue_autoplay | ||||
|  | ||||
|   @[JSON::Field(converter: Preferences::BoolToString)] | ||||
|   @[YAML::Field(converter: Preferences::BoolToString)] | ||||
|   property dark_mode : String = CONFIG.default_user_preferences.dark_mode | ||||
|   property latest_only : Bool = CONFIG.default_user_preferences.latest_only | ||||
|   property listen : Bool = CONFIG.default_user_preferences.listen | ||||
|   property local : Bool = CONFIG.default_user_preferences.local | ||||
|   property vr_mode : Bool = CONFIG.default_user_preferences.vr_mode | ||||
|   property show_nick : Bool = CONFIG.default_user_preferences.show_nick | ||||
|  | ||||
|   @[JSON::Field(converter: Preferences::ProcessString)] | ||||
|   property locale : String = CONFIG.default_user_preferences.locale | ||||
|  | ||||
|   @[JSON::Field(converter: Preferences::ClampInt)] | ||||
|   property max_results : Int32 = CONFIG.default_user_preferences.max_results | ||||
|   property notifications_only : Bool = CONFIG.default_user_preferences.notifications_only | ||||
|  | ||||
|   @[JSON::Field(converter: Preferences::ProcessString)] | ||||
|   property player_style : String = CONFIG.default_user_preferences.player_style | ||||
|  | ||||
|   @[JSON::Field(converter: Preferences::ProcessString)] | ||||
|   property quality : String = CONFIG.default_user_preferences.quality | ||||
|   @[JSON::Field(converter: Preferences::ProcessString)] | ||||
|   property quality_dash : String = CONFIG.default_user_preferences.quality_dash | ||||
|   property default_home : String? = CONFIG.default_user_preferences.default_home | ||||
|   property feed_menu : Array(String) = CONFIG.default_user_preferences.feed_menu | ||||
|   property related_videos : Bool = CONFIG.default_user_preferences.related_videos | ||||
|  | ||||
|   @[JSON::Field(converter: Preferences::ProcessString)] | ||||
|   property sort : String = CONFIG.default_user_preferences.sort | ||||
|   property speed : Float32 = CONFIG.default_user_preferences.speed | ||||
|   property thin_mode : Bool = CONFIG.default_user_preferences.thin_mode | ||||
|   property unseen_only : Bool = CONFIG.default_user_preferences.unseen_only | ||||
|   property video_loop : Bool = CONFIG.default_user_preferences.video_loop | ||||
|   property extend_desc : Bool = CONFIG.default_user_preferences.extend_desc | ||||
|   property volume : Int32 = CONFIG.default_user_preferences.volume | ||||
|  | ||||
|   module BoolToString | ||||
|     def self.to_json(value : String, json : JSON::Builder) | ||||
|       json.string value | ||||
|     end | ||||
|  | ||||
|     def self.from_json(value : JSON::PullParser) : String | ||||
|       begin | ||||
|         result = value.read_string | ||||
|  | ||||
|         if result.empty? | ||||
|           CONFIG.default_user_preferences.dark_mode | ||||
|         else | ||||
|           result | ||||
|         end | ||||
|       rescue ex | ||||
|         if value.read_bool | ||||
|           "dark" | ||||
|         else | ||||
|           "light" | ||||
|         end | ||||
|       end | ||||
|     end | ||||
|  | ||||
|     def self.to_yaml(value : String, yaml : YAML::Nodes::Builder) | ||||
|       yaml.scalar value | ||||
|     end | ||||
|  | ||||
|     def self.from_yaml(ctx : YAML::ParseContext, node : YAML::Nodes::Node) : String | ||||
|       unless node.is_a?(YAML::Nodes::Scalar) | ||||
|         node.raise "Expected scalar, not #{node.class}" | ||||
|       end | ||||
|  | ||||
|       case node.value | ||||
|       when "true" | ||||
|         "dark" | ||||
|       when "false" | ||||
|         "light" | ||||
|       when "" | ||||
|         CONFIG.default_user_preferences.dark_mode | ||||
|       else | ||||
|         node.value | ||||
|       end | ||||
|     end | ||||
|   end | ||||
|  | ||||
|   module ClampInt | ||||
|     def self.to_json(value : Int32, json : JSON::Builder) | ||||
|       json.number value | ||||
|     end | ||||
|  | ||||
|     def self.from_json(value : JSON::PullParser) : Int32 | ||||
|       value.read_int.clamp(0, MAX_ITEMS_PER_PAGE).to_i32 | ||||
|     end | ||||
|  | ||||
|     def self.to_yaml(value : Int32, yaml : YAML::Nodes::Builder) | ||||
|       yaml.scalar value | ||||
|     end | ||||
|  | ||||
|     def self.from_yaml(ctx : YAML::ParseContext, node : YAML::Nodes::Node) : Int32 | ||||
|       node.value.clamp(0, MAX_ITEMS_PER_PAGE) | ||||
|     end | ||||
|   end | ||||
|  | ||||
|   module FamilyConverter | ||||
|     def self.to_yaml(value : Socket::Family, yaml : YAML::Nodes::Builder) | ||||
|       case value | ||||
|       when Socket::Family::UNSPEC | ||||
|         yaml.scalar nil | ||||
|       when Socket::Family::INET | ||||
|         yaml.scalar "ipv4" | ||||
|       when Socket::Family::INET6 | ||||
|         yaml.scalar "ipv6" | ||||
|       when Socket::Family::UNIX | ||||
|         raise "Invalid socket family #{value}" | ||||
|       end | ||||
|     end | ||||
|  | ||||
|     def self.from_yaml(ctx : YAML::ParseContext, node : YAML::Nodes::Node) : Socket::Family | ||||
|       if node.is_a?(YAML::Nodes::Scalar) | ||||
|         case node.value.downcase | ||||
|         when "ipv4" | ||||
|           Socket::Family::INET | ||||
|         when "ipv6" | ||||
|           Socket::Family::INET6 | ||||
|         else | ||||
|           Socket::Family::UNSPEC | ||||
|         end | ||||
|       else | ||||
|         node.raise "Expected scalar, not #{node.class}" | ||||
|       end | ||||
|     end | ||||
|   end | ||||
|  | ||||
|   module URIConverter | ||||
|     def self.to_yaml(value : URI, yaml : YAML::Nodes::Builder) | ||||
|       yaml.scalar value.normalize! | ||||
|     end | ||||
|  | ||||
|     def self.from_yaml(ctx : YAML::ParseContext, node : YAML::Nodes::Node) : URI | ||||
|       if node.is_a?(YAML::Nodes::Scalar) | ||||
|         URI.parse node.value | ||||
|       else | ||||
|         node.raise "Expected scalar, not #{node.class}" | ||||
|       end | ||||
|     end | ||||
|   end | ||||
|  | ||||
|   module ProcessString | ||||
|     def self.to_json(value : String, json : JSON::Builder) | ||||
|       json.string value | ||||
|     end | ||||
|  | ||||
|     def self.from_json(value : JSON::PullParser) : String | ||||
|       HTML.escape(value.read_string[0, 100]) | ||||
|     end | ||||
|  | ||||
|     def self.to_yaml(value : String, yaml : YAML::Nodes::Builder) | ||||
|       yaml.scalar value | ||||
|     end | ||||
|  | ||||
|     def self.from_yaml(ctx : YAML::ParseContext, node : YAML::Nodes::Node) : String | ||||
|       HTML.escape(node.value[0, 100]) | ||||
|     end | ||||
|   end | ||||
|  | ||||
|   module StringToArray | ||||
|     def self.to_json(value : Array(String), json : JSON::Builder) | ||||
|       json.array do | ||||
|         value.each do |element| | ||||
|           json.string element | ||||
|         end | ||||
|       end | ||||
|     end | ||||
|  | ||||
|     def self.from_json(value : JSON::PullParser) : Array(String) | ||||
|       begin | ||||
|         result = [] of String | ||||
|         value.read_array do | ||||
|           result << HTML.escape(value.read_string[0, 100]) | ||||
|         end | ||||
|       rescue ex | ||||
|         result = [HTML.escape(value.read_string[0, 100]), ""] | ||||
|       end | ||||
|  | ||||
|       result | ||||
|     end | ||||
|  | ||||
|     def self.to_yaml(value : Array(String), yaml : YAML::Nodes::Builder) | ||||
|       yaml.sequence do | ||||
|         value.each do |element| | ||||
|           yaml.scalar element | ||||
|         end | ||||
|       end | ||||
|     end | ||||
|  | ||||
|     def self.from_yaml(ctx : YAML::ParseContext, node : YAML::Nodes::Node) : Array(String) | ||||
|       begin | ||||
|         unless node.is_a?(YAML::Nodes::Sequence) | ||||
|           node.raise "Expected sequence, not #{node.class}" | ||||
|         end | ||||
|  | ||||
|         result = [] of String | ||||
|         node.nodes.each do |item| | ||||
|           unless item.is_a?(YAML::Nodes::Scalar) | ||||
|             node.raise "Expected scalar, not #{item.class}" | ||||
|           end | ||||
|  | ||||
|           result << HTML.escape(item.value[0, 100]) | ||||
|         end | ||||
|       rescue ex | ||||
|         if node.is_a?(YAML::Nodes::Scalar) | ||||
|           result = [HTML.escape(node.value[0, 100]), ""] | ||||
|         else | ||||
|           result = ["", ""] | ||||
|         end | ||||
|       end | ||||
|  | ||||
|       result | ||||
|     end | ||||
|   end | ||||
|  | ||||
|   module StringToCookies | ||||
|     def self.to_yaml(value : HTTP::Cookies, yaml : YAML::Nodes::Builder) | ||||
|       (value.map { |c| "#{c.name}=#{c.value}" }).join("; ").to_yaml(yaml) | ||||
|     end | ||||
|  | ||||
|     def self.from_yaml(ctx : YAML::ParseContext, node : YAML::Nodes::Node) : HTTP::Cookies | ||||
|       unless node.is_a?(YAML::Nodes::Scalar) | ||||
|         node.raise "Expected scalar, not #{node.class}" | ||||
|       end | ||||
|  | ||||
|       cookies = HTTP::Cookies.new | ||||
|       node.value.split(";").each do |cookie| | ||||
|         next if cookie.strip.empty? | ||||
|         name, value = cookie.split("=", 2) | ||||
|         cookies << HTTP::Cookie.new(name.strip, value.strip) | ||||
|       end | ||||
|  | ||||
|       cookies | ||||
|     end | ||||
|   end | ||||
| end | ||||
|  | ||||
| def get_user(sid, headers, db, refresh = true) | ||||
|   if email = db.query_one?("SELECT email FROM session_ids WHERE id = $1", sid, as: String) | ||||
|     user = db.query_one("SELECT * FROM users WHERE email = $1", email, as: User) | ||||
|   | ||||
		Reference in New Issue
	
	Block a user
	 Samantaz Fox
					Samantaz Fox