#c# #database #winforms #entity-framework #tobase64string
Вопрос:
У меня проблема, когда я конвертирую изображение в строку Base64 и сохраняю его как строку в базе данных, но оно ничего не возвращает. Base64Text-глобальная переменная, также переменная не равна нулю, я проверил ее с помощью кнопки для заполнения текстового поля, она просто сохраняется как «» в базе данных.
Вот модель таблицы в базе данных
public class Product
{
public int Id { get; set; }
public string ProductName { get; set; }
public double ProductPrice { get; set; }
public int ProductAmount { get; set; }
public string ProductImage { get; set; } // Used for storing image string
public int userID { get; set; }
}
// Here is image converter
private void btnAddImage_Click(object sender, EventArgs e)
{
OpenFileDialog dialog = new OpenFileDialog();
dialog.Filter = "Image Files(*.BMP;*.JPG;*.PNG;*.JPEG)|*.BMP;*.JPG;*.PNG;*.JPEG"
"|All files(*.*)|*.*";
dialog.CheckFileExists = true;
dialog.Multiselect = false;
if (dialog.ShowDialog() == DialogResult.OK)
{
var image = new Bitmap(dialog.FileName);
pictureBoxProductImage.Show();
pictureBoxProductImage.Image = (Image)image;
byte[] imageArray = System.IO.File.ReadAllBytes(dialog.FileName);
base64Text = Convert.ToBase64String(imageArray);
}
}
// Here is saving image using Entity framework
private void btnAddProduct_Click(object sender, EventArgs e)
{
string imagePath = base64Text;
if (txtBoxProductName.Text == null || txtBoxProductPrice.Text == null || txtBoxProductQuantity.Text == null || imagePath == null || imagePath == "")
{
MessageBox.Show("Please fill required information!", "", MessageBoxButtons.OK);
}
else
{
model.ProductName = txtBoxProductName.Text;
model.ProductPrice = Convert.ToDouble(txtBoxProductPrice.Text);
model.ProductAmount = Convert.ToInt32(txtBoxProductQuantity.Text);
model.ProductImage = imagePath;
model.userID = id;
using (var context = new ProductContext())
{
context.Products.Add(model);
context.SaveChanges();
}
MessageBox.Show("Product sucesffuly added to database!", "", MessageBoxButtons.OK);
Clear();
}
}
Комментарии:
1. На первый взгляд я заметил, что вы преобразуете все изображение в base64, а не только путь! Во-вторых, не могли бы вы показать нам DbContext? и вы просматривали содержимое базы данных после операции сохранения?
2. Все остальные данные были сохранены правильно, как написано, ожидайте, что строка изображения будет»», поэтому мне нужен путь сохранения, а не строка base64?
3. Можете ли вы предоставить дополнительную информацию о том, на какую версию EF вы ориентируетесь и какую базу данных вы используете? binaryintellect.net/articles/… Я бы предложил следовать приведенному выше примеру… обратите особое внимание на конфигурацию сущности и массив байтов из потока памяти, скопированного в метод
4. Где вы создаете экземпляр сущности продукта? возможно, вы установили его свойство image где-то в другом месте после его сохранения, и EF все еще отслеживает этот объект, и в другой транзакции сохранения он сбрасывается до нуля
5. Поскольку вы сохраняете все изображение в качестве base64, а не только путь, я думаю, что вы можете достичь некоторого предела в своей таблице, так как результат base64 будет длинным. Я рекомендую вам сохранить только путь или использовать другой тип данных для хранения двоичного файла-если файл недоступен локально на всех компьютерах или недоступен онлайн-.
Ответ №1:
Похоже, вы опасно смешиваете переменные области. Учитывая этот код:
model.ProductName = txtBoxProductName.Text;
model.ProductPrice = Convert.ToDouble(txtBoxProductPrice.Text);
model.ProductAmount = Convert.ToInt32(txtBoxProductQuantity.Text);
model.ProductImage = imagePath;
model.userID = id;
using (var context = new ProductContext())
{
context.Products.Add(model);
context.SaveChanges();
}
«модель» не относится к этому методу.
Я не рекомендую привязывать представления к сущностям в качестве моделей представлений, вместо этого используйте простой старый класс C# ViewModel, чтобы избежать путаницы и проблем с объектами, вызывающими множество проблем. (Отслеживание изменений свойств, поведение проверки пользовательского интерфейса и т.д.)
На что это должно больше походить:
using (var context = new ProductContext())
{
var product = new Product
{
UserId = id,
ProductName = txtBoxProductName.Text,
ProductPrice = Convert.ToDouble(txtBoxProductPrice.Text),
ProductAmount = Convert.ToInt32(txtBoxProductQuantity.Text),
ProductImage = hiddenImage.Text, // Something in the scope of the view storing the image Base64 content, not a global variable.
};
context.Products.Add(product);
context.SaveChanges();
}
При добавлении сущности вы хотите убедиться, что имеете дело с новым экземпляром этой сущности, а не со ссылкой. model
это может быть ссылка на другую сущность, которую контекст уже отслеживает, что означает, что вы можете в конечном итоге заменить значения в совершенно другой записи, когда думаете, что добавляете новую строку. Кроме того, поскольку вы определяете область действия нового экземпляра DbContext, любая ссылка на сущность за пределами этой области может привести к исключениям.
Избегайте глобальных переменных для любых деталей. При выборе изображения убедитесь, что Base64 хранится где-то в области страницы приложения или модели связанного представления. Если после этих изменений по-прежнему не сохраняется ProductImage, я бы посмотрел на объявление сущности , чтобы убедиться, что оно не помечено как Ignore
, и рассмотрел возможность использования профилировщика для проверки создаваемого SQL, чтобы убедиться, что поле включено и какое значение отправляется.