Python入门自学进阶-Web框架——28、DjangoAdmin项目应用-只读字段与后端表单验证

news2024/11/15 14:00:11

有时候,记录的某些字段在生成后就不允许再修改了,这时前端只能显示,不能修改。这时,可在AdminClass中进行设置:readonly_fields=[字段名,字段名,。。。],前端格式就显示成只显示不能修改。实现如下:

 在对应的input标签中增加disabled属性,就可以禁止修改,但问题是,这是在前端页面进行的修改,而我们的修改页面,即rec_change.html中,是直接{{ f }}生成的标签,即使用的modelform标签,所以,要修改,只能在后端对modelform进行修改。

对创建动态modelform进行修改:

def create_model_form(req,admin_class):
    # 动态生成ModelForm类,主要使用type函数
    def __new__(cls, *args, **kwargs):
        # 対生成ModelForm中的字段添加前端样式,即在前端自动生成标签时带上class属性
        # cls.base_fields['qq'].widget.attrs['class'] = 'form-control'
        print("22222222",cls,cls.base_fields)  # cls是动态生成的Modelform,cls.base_fields是字段的列表
        for field_name,field_obj in cls.base_fields.items():
            print(field_name,"<---->",field_obj)
            if field_name in admin_class.readonly_fields:
                field_obj.widget.attrs['disabled'] = 'disabled'

        return ModelForm.__new__(cls)
    class Meta:
        model = admin_class.model
        fields = "__all__"
    print("111111111111")
    model_form_class = type("DynamicModelForm",(ModelForm,),{'Meta':Meta})
    print("33333333")
    setattr(model_form_class,'__new__',__new__)  # 以这种方式给动态生成的类加Meta不好用
    print('444444444444')
    return model_form_class

打印的1111111、2222等是为了测试执行顺序,__new__中的cls就是动态生成的ModelForm类,其base_fields是ModelForm类对应的Model类中的字段字典:

 这样在前端生成的标签,qq就不能修改了,但是在提交时,即点击保存按钮时,提示错误,qq字段不能为空,也就是标签被设置为disabled后,提交时其值不会被提交。

使用readonly属性,对于input标签可以做到就不能修改,也能提交,但是此属性对于下拉框不起作用,所以另想一个办法,在数据提交到后端后,对提交的数据进行修改:

修改前:

def rec_obj_change(req,app_name,table_name,id_num):
    admin_class = mytestapp_admin.enable_admins[app_name][table_name]
    model_form_class = myutils.create_model_form(req,admin_class)
    obj = admin_class.model.objects.get(id=id_num)

    if req.method == "POST":
        print('第二次POST')
        form_obj = model_form_class(req.POST,instance=obj)
        # ModelForm参数为一个时,是新建一条记录,当有两个参数时,就是修改
        # POST方法就是进行记录修改的,所以需要两个参数,第二个是instance=参数
        if form_obj.is_valid():
            form_obj.save()

    else:    # 这是GET请求,所以是新建一个ModelForm,进行显示
        print('第一次GET')
        form_obj = model_form_class(instance=obj)
    return render(req,'mytestapp/rec_change.html',{'form_obj':form_obj,'model_name':admin_class.model.__name__,'admin_class':admin_class})

对上面的代码,在判断为POST方法后,尝试对req.POST修改,将obj对应的字段及其值再加入POST中,实测中,提示req.POST是不可修改的,所以,做一个拷贝:

    if req.method == "POST":
        print('第二次POST')
        # for field in admin_class.readonly_fields:
        #     req.POST[field] = getattr(obj,field)    # 不能修改POST,此方法不可行
        post_data = req.POST.copy()   # 对POST做一个拷贝,使用可变的副本进行修改
        for field in admin_class.readonly_fields:
            post_data[field] = getattr(obj,field)

        form_obj = model_form_class(post_data,instance=obj)

这里有一个在添加post_data的readonly_fields字段时,这里如果将consultant字段加入readonly_fields中,在后端加入post_data的是post_data['consultant'] = getattr(obj,field),值是一个对象,(如这里添加的consultant是 <class 'plcrm.models.UserProfile'>类型),而从前端提交时,通过下拉框选择,传递的是一个字符串格式的数字,即UserProfile的id。

修改前端,在提交时,将disabled属性去掉,这样对应的字段值就能提交了。

在rec_change.html中,将form提交时执行的函数SelectedAll()进行如下修改:

function SelectedAll() {
            $("select[my_id='selectedalloption'] option").each(function () {
                $(this).prop("selected",true)
            });
            $("form").find("[disabled]").removeAttr("disabled");
            return true

        }

主要是增加将disabled属性去掉的语句,这时再提交,后端视图函数打印POST如下:

@@@ <QueryDict: {'csrfmiddlewaretoken': ['59Ef3Jme9aQawB9jiZl9Y1CAHwHNkr1ybCy63izXnjJ6wjT519DH62rD16ZvfnpK'], 'name': ['老舍46667'], 'qq': ['2111111111'], 'qq_name': ['反反复复'], 'phone': ['13212345678'], 'source': ['5'], 'referral_from': ['1234554'], 'consult_course': ['1'], 'content': ['反反复复发发发发发发ppppp'], 'tags': ['1', '3', '5'], 'status': ['1'], 'consultant': ['3'], 'memo': ['巴巴爸爸不不不不不不不']}>

此时,视图函数rec_obj_change就不需要修改了。修改功能完成。

前端通过修改成disabled的方法,是可以通过调试将其改回去的,其无法保证传递到后端的数据不变,所以,还需要在后端进行一次验证。

Form验证,使用自定义的clean方法,修改动态生成的ModelForm,添加自定义的clean方法:

def create_model_form(req,admin_class):
    # 动态生成ModelForm类,主要使用type函数
    def __new__(cls, *args, **kwargs):
        # 対生成ModelForm中的字段添加前端样式,即在前端自动生成标签时带上class属性
        # cls.base_fields['qq'].widget.attrs['class'] = 'form-control'
        print("22222222",cls,cls.base_fields)  # cls是动态生成的Modelform,cls.base_fields是字段的列表
        for field_name,field_obj in cls.base_fields.items():
            print(field_name,"<---->",field_obj)
            if field_name in admin_class.readonly_fields:
                field_obj.widget.attrs['disabled'] = 'disabled'

        return ModelForm.__new__(cls)
    def default_clean(self):
        '''给所有的form添加一个默认的clean验证'''
        print('======运行自定义clean验证=======:',self)

    class Meta:
        model = admin_class.model
        fields = "__all__"

    model_form_class = type("DynamicModelForm",(ModelForm,),{'Meta':Meta})
    setattr(model_form_class,'__new__',__new__)  # 以这种方式给动态生成的类加Meta不好用
    setattr(model_form_class,'clean',default_clean)
    return model_form_class

打印的结果:

 可以看出,self就是页面中form表单内的内容。

将print('======运行自定义clean验证=======:',self)改成
print('======运行自定义clean验证=======:',admin_class.readonly_fields),打印出readonly字段,然后对该字段进行验证,即取前端传递过来的数据,与数据库中已有的数据进行比较,如果相同,说明前端确实没有修改,否则,就是被人为越过前端的disabled属性,修改了,此时要报错。

from django.forms import ValidationError
from django.utils.translation import ugettext as _
def create_model_form(req,admin_class):
    # 动态生成ModelForm类,主要使用type函数
    def __new__(cls, *args, **kwargs):
        # 対生成ModelForm中的字段添加前端样式,即在前端自动生成标签时带上class属性
        # cls.base_fields['qq'].widget.attrs['class'] = 'form-control'
        print("22222222",cls,cls.base_fields)  # cls是动态生成的Modelform,cls.base_fields是字段的列表
        for field_name,field_obj in cls.base_fields.items():
            print(field_name,"<---->",field_obj)
            if field_name in admin_class.readonly_fields:
                field_obj.widget.attrs['disabled'] = 'disabled'

        return ModelForm.__new__(cls)
    def default_clean(self):
        '''给所有的form添加一个默认的clean验证'''
        print('======运行自定义clean验证=======:',admin_class.readonly_fields)
        for field in admin_class.readonly_fields:
            field_val_db = getattr(self.instance,field) # 从数据库中来的数据
            field_val_web = self.cleaned_data.get(field) # 从前端web页传递过来的数据
            print("----field compare:",field,field_val_db,field_val_web)
            if field_val_db != field_val_web:
                raise ValidationError(
                    _('Field %(field)s is readonly,data should be %(val)s'),
                    code='invalid',
                    params={'field':field,'val':field_val_db}
                )


    class Meta:
        model = admin_class.model
        fields = "__all__"

    model_form_class = type("DynamicModelForm",(ModelForm,),{'Meta':Meta})
    setattr(model_form_class,'__new__',__new__)  # 以这种方式给动态生成的类加Meta不好用
    setattr(model_form_class,'clean',default_clean)
    return model_form_class

关键看上面的default_clean函数,对前端数据和后端数据进行校验,如果出错,提示:

 我同时修改了qq和consultant,但是错误只显示了一个,说明在default_clean中,碰到第一个raise,程序就跳出,没有执行第二个字段的判断。

再次修改default_clean:

    def default_clean(self):
        '''给所有的form添加一个默认的clean验证'''
        print('======运行自定义clean验证=======:',admin_class.readonly_fields)
        error_list = []
        for field in admin_class.readonly_fields:
            field_val_db = getattr(self.instance,field) # 从数据库中来的数据
            field_val_web = self.cleaned_data.get(field) # 从前端web页传递过来的数据
            print("----field compare:",field,field_val_db,field_val_web)
            if field_val_db != field_val_web:
                error_list.append(ValidationError(
                    _('Field %(field)s is readonly,data should be %(val)s'),
                    code='invalid',
                    params={'field':field,'val':field_val_db}
                ))
        if error_list:
            raise ValidationError(error_list)

此时在测试:

 因为在动态生成的ModelForm中定义了自己的clean方法,就是上面的default_clean,这就阻断了原来用户可以重写clean方法来自定义自己的验证,如何让用户能够继续自定义自己的验证呢?可以在AdminClass中定义一个函数,用户可以覆写这个函数,在我们动态生成的ModelForm的clean方法中,最后调用一下用户自定义的函数就好了。

    
def default_clean(self):
        '''给所有的form添加一个默认的clean验证'''
        print('======运行自定义clean验证=======:',admin_class.readonly_fields)
        error_list = []
        for field in admin_class.readonly_fields:
            field_val_db = getattr(self.instance,field) # 从数据库中来的数据
            field_val_web = self.cleaned_data.get(field) # 从前端web页传递过来的数据
            print("----field compare:",field,field_val_db,field_val_web)
            if field_val_db != field_val_web:
                error_list.append(ValidationError(
                    _('Field %(field)s is readonly,data should be %(val)s'),
                    code='invalid',
                    params={'field':field,'val':field_val_db}
                ))

        self.ValidationError = ValidationError
        user_return = admin_class.user_form_validation(self)
        if user_return:
            error_list.append(user_return)
        if error_list:
            raise ValidationError(error_list)


# 在admin.py中
class BaseAdmin(object):
    list_display = []
    list_filter = []
    list_per_page = 5
    list_search = []
    filter_horizontal = []
    readonly_fields = []
    actions = ['delete_action',]
    def delete_action(self,req,model_objs):
        print(self,req,model_objs)

    def user_form_validation(self):
        pass
        # 给用户自定义留下接口

class CustomerAdmin(BaseAdmin):
    list_display = ['qq','name','phone','source','consultant','referral_from','consult_course','tags','status']
    list_per_page = 4
    list_filter = ['qq','source','status','consult_course','tags']
    list_search = ['qq','name']
    filter_horizontal = ['tags']
    readonly_fields = ['qq','consultant']
    actions = ['delete_action',]
    def delete_action(self,req,model_objs):
        print("运行delete_action",self,req,model_objs)
        #  跳转到rec_delete.html,借助已经实现的功能,调用rec_obj_delete(req,app_name,table_name,id_num):
        # return render(req,'mytestapp/rec_delete.html',{})  #需要改造,匹配rec_obj_delete的参数
        model_objs.delete()
        print("删除执行完毕")
    def user_form_validation(self):    # 用户自定义验证
        print('-----user validation:',self)
        consult_content = self.cleaned_data.get("content",'')
        if len(consult_content):
            return self.ValidationError(('Field %(field)s 字段内容长度必须大于15'),
                    code='invalid',
                    params={'field':"content"}
                )

前面的clean方法是对全部字段的验证,Django还提供单个字段的验证,即clean_{filed}的验证方法:

在AdminClass中增加一个单字段验证函数:

#  在CustomerAdmin中定义
    def clean_name(self):
        print('****单字段验证',self.cleaned_data['name'])
        if not self.cleaned_data['name']:
            self.add_error('name','名字字段内容不能为空')

# 在创建动态ModelForm类中,增加单字段验证:
def create_model_form(req,admin_class):
    # 动态生成ModelForm类,主要使用type函数
    def __new__(cls, *args, **kwargs):
        # 対生成ModelForm中的字段添加前端样式,即在前端自动生成标签时带上class属性
        # cls.base_fields['qq'].widget.attrs['class'] = 'form-control'
        print("22222222",cls,cls.base_fields)  # cls是动态生成的Modelform,cls.base_fields是字段的列表
        for field_name,field_obj in cls.base_fields.items():
            print(field_name,"<---->",field_obj)
            if field_name in admin_class.readonly_fields:
                field_obj.widget.attrs['disabled'] = 'disabled'
            if hasattr(admin_class,'clean_%s'%field_name):  # 动态生成的类中增加单字段校验
                field_validat_fuc = getattr(admin_class,'clean_%s'%field_name)
                setattr(cls,'clean_%s'%field_name,field_validat_fuc)
        return ModelForm.__new__(cls)
    def default_clean(self):
        '''给所有的form添加一个默认的clean验证'''
        print('======运行自定义clean验证=======:',admin_class.readonly_fields)
        error_list = []
        for field in admin_class.readonly_fields:
            field_val_db = getattr(self.instance,field) # 从数据库中来的数据
            field_val_web = self.cleaned_data.get(field) # 从前端web页传递过来的数据
            print("----field compare:",field,field_val_db,field_val_web)
            if field_val_db != field_val_web:
                error_list.append(ValidationError(
                    _('Field %(field)s is readonly,data should be %(val)s'),
                    code='invalid',
                    params={'field':field,'val':field_val_db}
                ))

        self.ValidationError = ValidationError
        user_return = admin_class.user_form_validation(self)
        if user_return:
            error_list.append(user_return)
        if error_list:
            raise ValidationError(error_list)

    class Meta:
        model = admin_class.model
        fields = "__all__"

    model_form_class = type("DynamicModelForm",(ModelForm,),{'Meta':Meta})
    setattr(model_form_class,'__new__',__new__)  # 以这种方式给动态生成的类加Meta不好用
    setattr(model_form_class,'clean',default_clean)
    return model_form_class

在前端,即rec_change.html中,在{{f}}后加上{{ f.errors }},这样在对应字段后显示错误信息,如下

 上面的readonly设置只对ModelForm自动生成的标签起作用,对于我们自定义的标签,如tags标签,因为配置了 filter_horizontal = ['tags']  ,在页面是自定义的显示为左右两个下拉复选框,未选项和已选项分别显示在不同框中,这时设置了readonly,需要同时disabled两个框。同时要去掉对应的事件函数,这主要是前端操作。修改rec_change.html:

{% if f.name in admin_class.filter_horizontal %}
    <div class="col-md-2" >
        {% get_m2m_obj_list admin_class f form_obj as m2m_obj_list %}
        {% if f.name in admin_class.readonly_fields %}
            <select id="noselected_{{ f.name }}" multiple class="select-box" name="{{ f.name }}" disabled>
                 {% for obj in m2m_obj_list %}
                     <option value="{{ obj.id }}">{{ obj }}</option>
                 {% endfor %}
             </select>
        {% else %}
            <select id="noselected_{{ f.name }}" multiple class="select-box" name="{{ f.name }}">
                 {% for obj in m2m_obj_list %}
                     <option value="{{ obj.id }}" ondblclick="MoveToSelected(this,'selected_{{ f.name }}','noselected_{{ f.name }}')">{{ obj }}</option>
                 {% endfor %}
             </select>
        {% endif %}
    </div>
    <div class="col-md-1">
        ===》<br>
        《===
    </div>
    <div class="col-md-2">
        {% if f.name in admin_class.readonly_fields %}
            <select my_id="selectedalloption" id="selected_{{ f.name }}" multiple class="select-box" name="{{ f.name }}" disabled>
                {% get_m2m_selected_list form_obj f as selected_list %}
                 <!-- 上面是使用自定义标签获取已选择项数据-->
                 <!-- 下面是经过测试,使用f的initial也能获取到,不需要再定义标签 -->
                 {% for obj in selected_list %}
                    <option value="{{ obj.id }}" >{{ obj }}</option>
                 {% endfor %}
            </select>
        {% else %}
            <select my_id="selectedalloption" id="selected_{{ f.name }}" multiple class="select-box" name="{{ f.name }}">
                {% get_m2m_selected_list form_obj f as selected_list %}
                 <!-- 上面是使用自定义标签获取已选择项数据-->
                 <!-- 下面是经过测试,使用f的initial也能获取到,不需要再定义标签 -->
                 {% for obj in selected_list %}
                    <option value="{{ obj.id }}" ondblclick="MoveToSelected(this,'noselected_{{ f.name }}','selected_{{ f.name }}')">{{ obj }}</option>
                 {% endfor %}
            </select>
        {% endif %}
    </div>
{% else %}
        {{ f }}<span>{{ f.errors }}</span>
{% endif %}

再次测试:

 tags无法操作了,但是,在提交保存时,出现了验证错误:

 打印传递的参数:request.POST中如下

 自定义验证中:

 对应的取数语句:
field_val_db = getattr(self.instance,field) # 从数据库中来的数据
field_val_web = self.cleaned_data.get(field) # 从前端web页传递过来的数据
print("----field compare:",field,field_val_db,field_val_web)

也就是从数据库中的取数,对于tags出现了错误,对于多对多的字段,需要判断是否存在select_related属性,存在,将这个属性值取出,因为是QuerySet,不能直接使用==判断,因为顺序不一样的话,也不相等,可以都转换为set:

def default_clean(self):
        '''给所有的form添加一个默认的clean验证'''
        print('======运行自定义clean验证=======:',admin_class.readonly_fields)
        print('&&&self.instance',type(self.instance))
        error_list = []
        for field in admin_class.readonly_fields:
            field_val_db = getattr(self.instance,field) # 从数据库中来的数据
            if hasattr(field_val_db,'select_related'):   # 如果是多对多字段,取select_related(),
                field_val_db = set(field_val_db.select_related())  # 数据库值转换为set
                field_val_web = set(self.cleaned_data.get(field))  # 前端数据也转换为set
            else:
                field_val_web = self.cleaned_data.get(field) # 从前端web页传递过来的数据
            print("----field compare:",field,field_val_db,field_val_web)
            if field_val_db != field_val_web:
                error_list.append(ValidationError(
                    _('Field %(field)s is readonly,data should be %(val)s'),
                    code='invalid',
                    params={'field':field,'val':field_val_db}
                ))

        self.ValidationError = ValidationError
        user_return = admin_class.user_form_validation(self)
        if user_return:
            error_list.append(user_return)
        if error_list:
            raise ValidationError(error_list)

有一个问题:在单字段验证后,即clean_name(self)执行后,在用户自定义的验证中,这个字段的值就没有了,变成了None,导致最终保存后,name字段一直为空。

修改clean_name(self):

    def clean_name(self):
        print('****单字段验证',self.cleaned_data)
        print('**单字段验证的参数self',self.cleaned_data['name'])
        if not self.cleaned_data['name']:
            self.add_error('name','名字字段内容不能为空')
        print('***验证后:',self.cleaned_data)
        return self.cleaned_data['name']    # 这一句非常重要

注意,最后一句加上了返回值,非常重要的一步。看下面的解析:

clean_<fieldname>() 方法是在表单子类上调用的——其中 <fieldname> 被替换为表单字段属性的名称。这个方法做任何特定属性的清理工作,与字段的类型无关。这个方法不传递任何参数。你需要在 self.cleaned_data 中查找字段的值,并且记住,此时它将是一个 Python 对象,而不是在表单中提交的原始字符串(它将在 cleaned_data 中,因为上面的一般字段 clean() 方法已经清理了一次数据)。

例如,如果你想验证一个叫 serialnumber 的 CharField 的内容是唯一的,clean_serialnumber() 就可以做这件事。你不需要一个特定的字段(它是一个 CharField),但你需要一个特定字段的验证,可能的话,清理/规范数据。

这个方法的返回值会替换 cleaned_data 中的现有值,所以它必须是 cleaned_data 中的字段值(即使这个方法没有改变它)或一个新的干净值。

当没有最后一句时,默认返回值就是None。

添加新纪录时,就不需要进行readonly_fields判断了:

视图函数:

def rec_obj_add(req,app_name,table_name):
    admin_class = mytestapp_admin.enable_admins[app_name][table_name]
    admin_class.add_form = True  # 为调用动态生成ModelForm,区分是修改还是增加的标志
    model_form_class = myutils.create_model_form(req, admin_class)
    if req.method == "POST":
        print("添加的POST内容:",req.POST)
        form_obj = model_form_class(req.POST)
        # ModelForm参数为一个时,是新建一条记录,POST方法提交,是新建一条记录
        if form_obj.is_valid():
            form_obj.save()
            return redirect(req.path.replace("/add/","/"))
    else:    # 这是GET请求,所以是新建一个空ModelForm
        form_obj = model_form_class()
    return render(req,"mytestapp/rec_add.html",{'admin_class':admin_class,'model_name':admin_class.model.__name__,'form_obj':form_obj})

注意在调用生成动态ModelForm前,在admin_class中增加一个add_form属性,以此在create_model_form中判断是修改操作还是添加操作。

对create_model_form进行修改:主要是__new__()函数修改

    def __new__(cls, *args, **kwargs):
        # 対生成ModelForm中的字段添加前端样式,即在前端自动生成标签时带上class属性
        # cls.base_fields['qq'].widget.attrs['class'] = 'form-control'
        print("22222222")  # cls是动态生成的Modelform,cls.base_fields是字段的列表
        for field_name,field_obj in cls.base_fields.items():
            # print(field_name,"<---->",field_obj)
            if not hasattr(admin_class,"add_form"):    # 判断是否是添加操作,如果不是,则进行readonly_fields字段加disabled属性操作
                if field_name in admin_class.readonly_fields:
                    field_obj.widget.attrs['disabled'] = 'disabled'
            if hasattr(admin_class,'clean_%s'%field_name):  # 动态生成的类中增加单字段校验
                field_validat_fuc = getattr(admin_class,'clean_%s'%field_name)
                setattr(cls,'clean_%s'%field_name,field_validat_fuc)
        print('222222222结束')
        return ModelForm.__new__(cls)

对于空字段的单字段校验,如果添加时字段没有数据,为空,单字段校验应该提示错误信息,然后停留在添加页,但是实际测试中出现错误:

 原因是单字段验证,对于POST中name=['']没有添加到cleaned_data中,修改一下:

    def clean_name(self):
        print('****单字段验证',self.cleaned_data)
        print('**单字段验证的参数self',self.cleaned_data['name'])
        if not self.cleaned_data['name']:
            self.add_error('name','名字字段内容不能为空')
            self.cleaned_data['name']=None  # 如果为空,在cleaned_data中没有name这个属性,手工加上
            print("进入单字段验证")
        print('***验证后:',self.cleaned_data)
        return self.cleaned_data['name']    # 这一句非常重要

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/71317.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

联想电脑怎么录屏?这3个方法,轻松解决

录屏是现在最常见的办公功能之一&#xff0c;最近有朋友问联想电脑怎么录屏。联想电脑是使用Windows系统的。如果想用联想电脑录屏&#xff0c;可以使用Windows系统自带了的录屏软件进行录屏。下面小编将详细的介绍3个方法&#xff0c;解决联想电脑怎么录屏的问题&#xff0c;感…

8086寻址方式图解

目录 1&#xff1a;立即寻址 2&#xff1a;寄存器寻址 3&#xff1a;直接寻址&#xff08;存储器直接寻址&#xff09; 4&#xff1a;寄存器间接寻址&#xff08;重点&#xff09; 5&#xff1a;基址寻址&#xff08;相对寻址&#xff09; 6&#xff1a;变址寻址 &#x…

后端程序员必备的Linux基础知识+常见命令(2023年最新版教程)

文章目录[1. 从认识操作系统开始](https://link.juejin.cn?targethttps%3A%2F%2Fsnailclimb.gitee.io%2Fjavaguide%2F%23%2Fdocs%2Foperating-system%2Flinux%3Fid%3D_1-%E4%BB%8E%E8%AE%A4%E8%AF%86%E6%93%8D%E4%BD%9C%E7%B3%BB%E7%BB%9F%E5%BC%80%E5%A7%8B)[1.1. 操作系统简…

【与达梦同行】数据库coredump的配置方式与截断测试

一、简述 Core的意思是内存, Dump的意思是扔出来, 堆出来.开发和使用Unix程序时, 有时程序莫名其妙的down了, 却没有任何的提示(有时候会提示core dumped). 这时候可以查看一下有没有形如core.进程号的文件生成。在国产操作系统麒麟V10中运维的时候&#xff0c;经常遇见一个问…

一、OpenAI ChatGPT 注册使用

文章目录注册购买openai的官网问题今天早上在sheep公众号里面看到了关于openai 旗下研发的chatgpt的产品&#xff0c;去到chatgpt的网页&#xff0c;我们可以看到他的标语。ChatGPT: Optimizing Language Models for Dialogue 哈哈&#xff0c;我百度了一下&#xff0c;大概意…

文教资料杂志文教资料杂志社文教资料编辑部2022年第17期目录

语言文学研《文教资料》投稿&#xff1a;cn7kantougao163.com 从MRC认知模型看《释大》中的同源关系 苏楚然; 1-4 徐志摩《再别康桥》英译本对比分析——基于许渊冲诗译的“三美论” 牟逸飞;梁楚涵; 5-9 严歌苓小说“笑”书写的语言修辞学视角分析 孙婷婷; 10-12 …

得物云原生全链路追踪Trace2.0-采集篇

一、0xcc开篇 2020年3月&#xff0c;得物技术团队在三个月的时间内完成了整个交易体系的重构&#xff0c;交付了五彩石项目&#xff0c;业务系统也进入了微服务时代。系统服务拆分之后&#xff0c;虽然每个服务都会有不同的团队各司其职&#xff0c;但服务之间的依赖也变得复杂…

学1个月爬虫就月赚6000?别被骗了,老师傅告诉你爬虫的真实情况!

用爬虫赚外快的事情我也干了很多年&#xff0c;爬虫自然不在话下。 那么今天我来说说5个深入一点的爬虫问题&#xff0c;让你清楚爬虫的真实情况&#xff1a; 1.现在的爬虫接单真能1个月赚6000的快外&#xff1f; 2.初级爬虫只能接一些小单&#xff0c;怎样才算初级爬虫水平&…

Kafka ui 搭建以及使用

Kafka ui 序 kafka 本身没有自带相关的 ui 界面&#xff0c;但是很多时候没有页面意味着只有使用命令行进行相关操作如创建 topic、更改 topic 信息、重置 offset 等等。但实际使用中这种效果很差劲&#xff0c;我们一般还是会借助其他软件&#xff0c;实现对 kafka 的页面管…

windows服务器搭建原神私服教程(附客户端+服务端+环境配置)

今天给大家带来的是windows服务器搭建原神私服的教程&#xff0c;服务端搭建于私人windows服务器&#xff0c;客户端支持情况&#xff1a;PC、iOS支持国服 /国际服均可&#xff0c;Android仅支持国际服。本篇文章附有客户端和服务端环境配置文件&#xff0c;请大家按需下载使用…

MobileNet v1神经网络剖析

本文参考: MobileNet网络_-断言-的博客-CSDN博客_mobile-ne Conv2d中的groups参数&#xff08;分组卷积&#xff09;怎么理解&#xff1f; 【分组卷积可以减少参数量、且不容易过拟合&#xff08;类似正则化&#xff09;】_马鹏森的博客-CSDN博客_conv groups Pytorch Mobil…

阿里巴巴正式开源云原生应用脚手架

12 月 3 日&#xff0c;微服务 x 容器开源开发者 Meetup 上海站上&#xff0c;阿里云智能技术专家&#xff0c;云原生应用脚手架项目负责人良名宣布阿里巴巴云原生应用脚手架项目正式开源&#xff0c;并在现场做了相关内容介绍。本次开源的云原生应用脚手架是一款基于 Spring I…

监控Kubernetes集群证书过期时间的三种方案

前言 Kubernetes 中大量用到了证书, 比如 ca证书、以及 kubelet、apiserver、proxy、etcd等组件&#xff0c;还有 kubeconfig 文件。 如果证书过期&#xff0c;轻则无法登录 Kubernetes 集群&#xff0c;重则整个集群异常。 为了解决证书过期的问题&#xff0c;一般有以下几…

关于“堆”,看看这篇文章就够了(附堆的两种应用场景)

… &#x1f4d8;&#x1f4d6;&#x1f4c3;本文已收录至&#xff1a;数据结构 | C语言 更多知识尽在此专栏中!文章目录&#x1f4d8;前言&#x1f4d8;正文&#x1f4d6;认识堆&#x1f4d6;实现堆&#x1f4c3;结构&#x1f4c3;入堆&#x1f4c3;出堆&#x1f4c3;建堆算法…

新Crack:Neodynamic ZPLPrinter SDK for .NET Standard

适用于 .NET Standard V4.0.22.1206 的 Neodynamic ZPLPrinter Emulator SDK 添加对带有自定义字体设置的 ^BC 命令的支持。2022 年 12 月 7 日 - 16:03新版本特征 添加了对带有自定义字体设置的 ^BC 命令的支持。关于 Neodynamic ZPLPrinter Emulator SDK for .NET Standard 使…

在r语言中使用GAM(广义相加模型)进行电力负荷时间序列分析

广义相加模型&#xff08;GAM&#xff1a;Generalized Additive Model&#xff09;&#xff0c;它模型公式如下&#xff1a;有p个自变量&#xff0c;其中X1与y是线性关系&#xff0c;其他变量与y是非线性关系&#xff0c;我们可以对每个变量与y拟合不同关系&#xff0c;对X2可以…

动态规划入门

一、基本思想 一般来说&#xff0c;只要问题可以划分成规模更小的子问题&#xff0c;并且原问题的最优解中包含了子问题的最优解&#xff0c;则可以考虑用动态规划解决。动态规划的实质是分治思想和解决冗余&#xff0c;因此&#xff0c;动态规划是一种将问题实例分解为更小的、…

JAVA SCRIPT设计模式--结构型--设计模式之FlyWeight享元模式(11)

JAVA SCRIPT设计模式是本人根据GOF的设计模式写的博客记录。使用JAVA SCRIPT语言来实现主体功能&#xff0c;所以不可能像C&#xff0c;JAVA等面向对象语言一样严谨&#xff0c;大部分程序都附上了JAVA SCRIPT代码&#xff0c;代码只是实现了设计模式的主体功能&#xff0c;不代…

知识图谱-KGE-语义匹配-双线性模型(打分函数用到了双线性函数)-2014 :MLP

Knowledge Vault & MLP 【paper】 Knowledge Vault: A Web-Scale Approach to Probabilistic Knowledge Fusion 【简介】 本文是谷歌的研究者发表在 KDD 2014 上的工作&#xff0c;提出了一套方法用于自动挖掘知识&#xff0c;并构建成大规模知识库 Knowledge Vault&…

【Linux】期末复习

文章目录1. 认识Linux系统2. Shell命令3. VI编辑器的使用4. Shell脚本编程5. 实验部分1. 认识Linux系统 Linux特点 完全免费开发性多用户、多任务丰富的网络功能可靠安全、性能稳定支持多种平台 2.Linux系统的组成 内核Shell应用程序文件系统 3.Linux版本 Linux版本由形如x1.x2…